Sarath Mohan
Sarath Mohan

Reputation: 1398

Write logs to a file and console in spring boot project using log4j2.xml

I tried to create simple spring boot application in which the log should be printed in both console and to a file which is outside the project folder.The log is able to print in console but not able to write into file . I specified the file location(the file is not created,I think the file automatically generate)

Here is the dependency added

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

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

    <!-- Add Log4j2 Dependency -->
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-log4j2</artifactId>
    </dependency>
</dependencies>

Here is the log4j.xml file(location src/main/resources/log4j2.xml)

<?xml version="1.0" encoding="UTF-8"?>
<Configuration status="WARN" monitorInterval="30">
    <Properties>
        <Property name="LOG_PATTERN">
            %d{yyyy-MM-dd HH:mm:ss.SSS} %5p ${hostName} --- [%15.15t] %-40.40c{1.} : %m%n%ex
        </Property>
    </Properties>

    <Appenders>
        <Console name="ConsoleAppender" target="SYSTEM_OUT"
            follow="true">
            <PatternLayout pattern="${LOG_PATTERN}" />
        </Console>

        <!-- Rolling File Appender -->
        <RollingFile name="FileAppender"
            fileName="/home/ubuntu/Documents/eclipse/logs/log4j2-demo.log"
            filePattern="logs/log4j2-demo-%d{yyyy-MM-dd}-%i.log">
            <PatternLayout>
                <Pattern>${LOG_PATTERN}</Pattern>
            </PatternLayout>
            <Policies>
                <TimeBasedTriggeringPolicy interval="1" />
                <SizeBasedTriggeringPolicy size="10MB" />
            </Policies>
            <DefaultRolloverStrategy max="10" />
        </RollingFile>
    </Appenders>

    <Loggers>

        <Root level="debug">
            <AppenderRef ref="ConsoleAppender" />
            <AppenderRef ref="FileAppender" />
        </Root>
    </Loggers>
</Configuration>

I added the logging feature in main class

    import org.apache.logging.log4j.LogManager;

    import org.apache.logging.log4j.Logger;

    import org.springframework.boot.SpringApplication;

    import org.springframework.boot.autoconfigure.SpringBootApplication;

@SpringBootApplication
public class LoggingApplication {

    private static final Logger logger = LogManager.getLogger(LoggingApplication.class);


    public static void main(String[] args) {
        logger.info("in main class");
        logger.info("info logging is printed");
        logger.debug("logger debud is worked");
        logger.warn("logging warn is worked");
        SpringApplication.run(LoggingApplication.class, args);
    }

}

Here is the Console : enter image description here

Upvotes: 2

Views: 10961

Answers (3)

RAJKUMAR NAGARETHINAM
RAJKUMAR NAGARETHINAM

Reputation: 1518

Please follow the below approach, Here I have configured two appenders for a single logger. If you log anything using that logger name all the log messages will be sent to both the place. In your case both console and file.

 <logger name="pushnotification" level="debug" additivity="false">
            <appender-ref ref="NOTIFICATION-FILE-APPENDER" />
    <appender-ref ref="NOTIFICATION-CONSOLE-APPENDER" />
        </logger>

    <appender name="NOTIFICATION-CONSOLE-APPENDER" class="ch.qos.logback.core.ConsoleAppender">
            <encoder
        class="ch.qos.logback.classic.encoder.PatternLayoutEncoder">
        <pattern>[%date{yyyy-MM-dd HH:mm:ss}][%level][%c][%t] - %msg%n
        </pattern>
    </encoder>
        </appender>

    <appender name="NOTIFICATION-FILE-APPENDER"
            class="ch.qos.logback.core.rolling.RollingFileAppender">
            <file>${logs.home}/applogs/notification.log</file>
            <append>true</append>
        </appender>

Upvotes: 1

DEBENDRA DHINDA
DEBENDRA DHINDA

Reputation: 1193

You can do as follows :

application.properties

#####LOGGING. . . .
logging.level.org.springframework.web=ERROR
logging.level.com.hsc.adauth.*=DEBUG

# Logging pattern for the console
logging.pattern.console="%d{yyyy-MM-dd HH:mm:ss} - %msg%n"

# Logging pattern for file
logging.pattern.file= "%d{yyyy-MM-dd HH:mm:ss} [%thread] %-5level %logger{36} - %msg%n"

#output to a temp_folder/file(give your file path here)
logging.file=${java.io.tmpdir}/application.log

You can use AOP also for central logging in your application too.....

Upvotes: 2

josephtaylor.art
josephtaylor.art

Reputation: 132

The first thing I would do is try removing the logback binder from your classpath as outlined in the documentation.

So, your pom.xml config would end up containing an exclusion, like:

<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-web</artifactId>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter</artifactId>
    <exclusions>
        <exclusion>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-logging</artifactId>
        </exclusion>
    </exclusions>
</dependency>
<dependency>
    <groupId>org.springframework.boot</groupId>
    <artifactId>spring-boot-starter-log4j2</artifactId>
</dependency>

In addition, I would recommend not using the log4j API classes directly, but instead utilizing the sfl4j API. spring-boot is already configured to use SL4J with whatever binder you have configured on the classpath (in this case it's log4j).

So instead of using org.apache.logging.log4j.Logger I would use org.slfj.Logger for your logger class and create it with org.slf4j.LoggerFactory.getLogger(). The benefit of doing that over using the log4j classes directly is you can switch binders underneath slf4j without having to change all your code. Just in case you decide later you want to use logback or something else.

If you make that change to your pom, and use the slf4j APIs, I think the spring-boot auto-configuration will load your configuration and start logging to the file appender as well as the console.

Upvotes: 1

Related Questions