Master Spring Boot Logging: Configure Logback & SLF4J for Powerful Log Management

This guide explains why Logback is the preferred logging framework for Spring Boot, shows how to add the necessary dependencies, configure console and file appenders, customize log patterns, use rolling policies, apply filters, and optimize logging statements with placeholders, all illustrated with clean XML and Java code examples.

Java High-Performance Architecture
Java High-Performance Architecture
Java High-Performance Architecture
Master Spring Boot Logging: Configure Logback & SLF4J for Powerful Log Management

Preface

Logging is essential in projects. The popular frameworks log4j and logback share the same author; Logback is intended as the successor to log4j. SLF4J provides a façade, while Logback and log4j implement its interfaces. This article demonstrates how to use Logback + SLF4J in a Spring Boot application.

Why Use Logback

Logback, created by the author of log4j, is more efficient, works in many environments, and natively supports SLF4J. It is also the default logging framework bundled with Spring Boot.

Getting Started

Add Dependencies

Spring Boot already includes spring-boot-starter-logging, which brings in Logback and SLF4J. If you need the web starter, simply add:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>

Default Configuration

By default Spring Boot logs to the console. To write to a file, set logging.file or logging.path in application.properties (they are mutually exclusive). Additional properties such as logging.level.<package> and logging.pattern.console control log levels and formats.

logback‑spring.xml Details

Spring Boot recommends naming the configuration file logback-spring.xml (instead of logback.xml) and placing it under src/main/resources. A custom name can be used by setting logging.config=classpath:your‑config.xml.

Core Concepts

Logback revolves around three main components:

Logger : the entry point for logging statements.

Appender : the destination (console, file, etc.).

Layout/Encoder : defines the output format.

Basic XML Example

<configuration>
    <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>%d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n</pattern>
        </encoder>
    </appender>
    <root level="DEBUG">
        <appender-ref ref="STDOUT"/>
    </root>
</configuration>

Elements Overview

Elements such as <logger>, <root>, and <appender> can have attributes like name, level, and additivity. Level inheritance follows the hierarchy unless explicitly overridden.

Appender Types

ConsoleAppender writes logs to the console. RollingFileAppender writes to a file and rolls over based on size or time.

Rolling Policies

TimeBasedRollingPolicy rolls logs according to a time pattern (e.g., daily). SizeAndTimeBasedRollingPolicy combines time‑based rolling with a size limit.

Encoder Pattern Example

%d{yyyy-MM-dd HH:mm:ss.SSS} %highlight(%-5level) --- [%15.15(%thread)] %cyan(%-40.40(%logger{40})) : %msg%n

This pattern prints the timestamp, colored level, thread, logger name, and the message.

Filters

Two common filters are LevelFilter (matches a specific level) and ThresholdFilter (blocks events below a threshold). Example using LevelFilter to allow only INFO level:

<appender name="CONSOLE" class="ch.qos.logback.core.ConsoleAppender">
    <filter class="ch.qos.logback.classic.filter.LevelFilter">
        <level>INFO</level>
        <onMatch>ACCEPT</onMatch>
        <onMismatch>DENY</onMismatch>
    </filter>
    <encoder>
        <pattern>%-4relative [%thread] %-5level %logger{30} - %msg%n</pattern>
    </encoder>
</appender>

Full logback‑spring.xml Example

<?xml version="1.0" encoding="UTF-8"?>
<configuration debug="true">
    <!-- Console appender -->
    <appender name="STDOUT" class="ch.qos.logback.core.ConsoleAppender">
        <encoder>
            <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %highlight(%-5level) --- [%15.15(%thread)] %cyan(%-40.40(%logger{40})) : %msg%n</pattern>
            <charset>UTF-8</charset>
        </encoder>
    </appender>

    <!-- INFO file appender -->
    <appender name="info_log" class="ch.qos.logback.core.rolling.RollingFileAppender">
        <File>logs/project_info.log</File>
        <append>true</append>
        <filter class="ch.qos.logback.classic.filter.LevelFilter">
            <level>ERROR</level>
            <onMatch>DENY</onMatch>
            <onMismatch>ACCEPT</onMismatch>
        </filter>
        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
            <fileNamePattern>logs/project_info.%d.%i.log</fileNamePattern>
            <maxHistory>30</maxHistory>
            <totalSizeCap>20GB</totalSizeCap>
            <maxFileSize>10MB</maxFileSize>
        </rollingPolicy>
        <encoder>
            <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %-5level --- [%15.15(%thread)] %-40.40(%logger{40}) : %msg%n</pattern>
            <charset>UTF-8</charset>
        </encoder>
    </appender>

    <!-- ERROR file appender -->
    <appender name="error_log" class="ch.qos.logback.core.rolling.RollingFileAppender">
        <File>logs/project_error.log</File>
        <append>true</append>
        <filter class="ch.qos.logback.classic.filter.ThresholdFilter">
            <level>ERROR</level>
        </filter>
        <rollingPolicy class="ch.qos.logback.core.rolling.SizeAndTimeBasedRollingPolicy">
            <fileNamePattern>logs/project_error.%d.%i.log</fileNamePattern>
            <maxHistory>30</maxHistory>
            <totalSizeCap>20GB</totalSizeCap>
            <maxFileSize>10MB</maxFileSize>
        </rollingPolicy>
        <encoder>
            <pattern>%d{yyyy-MM-dd HH:mm:ss.SSS} %-5level --- [%15.15(%thread)] %-40.40(%logger{40}) : %msg%n</pattern>
            <charset>UTF-8</charset>
        </encoder>
    </appender>

    <root level="INFO">
        <appender-ref ref="STDOUT"/>
    </root>

    <logger name="com.sailing.springbootmybatis" level="INFO">
        <appender-ref ref="info_log"/>
        <appender-ref ref="error_log"/>
    </logger>

    <logger name="com.sailing.springbootmybatis.mapper" level="DEBUG" additivity="false">
        <appender-ref ref="info_log"/>
        <appender-ref ref="error_log"/>
    </logger>

    <logger name="com.atomikos" level="INFO" additivity="false">
        <appender-ref ref="info_log"/>
        <appender-ref ref="error_log"/>
    </logger>
</configuration>

Additional Logging Tips

Typical logging statements:

Object entry = new SomeObject();
logger.debug("The entry is " + entry);

Creating the message string incurs a cost even when the log level is disabled. Guard the call:

if (logger.isDebugEnabled()) {
    Object entry = new SomeObject();
    logger.debug("The entry is " + entry);
}

The most efficient approach uses placeholders, which defer string construction until the message is actually logged:

Object entry = new SomeObject();
logger.debug("The entry is {}.", entry);

Multiple placeholders:

logger.debug("The new entry is {}. It replaces {}.", entry, oldEntry);
Object[] params = {newVal, below, above};
logger.debug("Value {} was inserted between {} and {}.", params);

To log an exception with its stack trace, include the exception as a separate argument:

logger.error("Program exception, details: {}", e.getLocalizedMessage(), e);
Original Source

Signed-in readers can open the original source through BestHub's protected redirect.

Sign in to view source
Republication Notice

This article has been distilled and summarized from source material, then republished for learning and reference. If you believe it infringes your rights, please contactadmin@besthub.devand we will review it promptly.

JavaloggingSpring BootXMLlogbackslf4j
Java High-Performance Architecture
Written by

Java High-Performance Architecture

Sharing Java development articles and resources, including SSM architecture and the Spring ecosystem (Spring Boot, Spring Cloud, MyBatis, Dubbo, Docker), Zookeeper, Redis, architecture design, microservices, message queues, Git, etc.

0 followers
Reader feedback

How this landed with the community

Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.