java - 将 log4j2 用于多个类

标签 java log4j

我找到了许多帮助我构建记录器的链接。一些在 SO 中,另一些在其他页面中。

这里的答案:https://stackoverflow.com/questions/7624895/how-to-use-log4j-with-multiple-classes#=是我发现的最好的。 这已经是多年以前的想法了,现在有些事情已经不同了。

我的目标是让所有将消息打印到日志(包括控制台和文件)的 java 类共享一个记录器。

我正在使用 LOG4J2:http://logging.apache.org/log4j/2.x/manual/configuration.html

ma​​in():

import org.apache.logging.log4j.Logger;

public class App {
    private static final Logger LOGGER = Logger.getLogger("GLOBAL");
    public static void main(){
        ...calling other classes
  }
}

任何其他类:

import org.apache.logging.log4j.Logger;
public class secondClass {
    private final Logger LOGGER = Logger.getLogger("GLOBAL");
    public void writeLog(){
      LOGGER.log(Level.INFO, "A simple string");
  }
}

log4j.xml

<?xml version="1.0" encoding="UTF-8"?>
<Configuration status="warn">
    <Properties>
        <Property name="basePath">/var/log</Property>
    </Properties>

    <Appenders>
        <RollingFile name="fileLogger" fileName="${basePath}/myApp.log" filePattern="${basePath}/myApp-%d{yyyy-MM-dd}.log">
            <PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n" />
            <Policies>
                <TimeBasedTriggeringPolicy interval="1" modulate="true" />
            </Policies>
        </RollingFile>

       <Console name="console" target="SYSTEM_OUT">
            <PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n" />
        </Console>
    </Appenders>
    <Loggers>
        <Logger name="java.util.logging.Logger" level="ALL" additivity="true">
            <appender-ref ref="fileLogger" level="ALL" />
        </Logger>
        <Root level="ALL" additivity="false">
            <appender-ref ref="console" />
        </Root>
    </Loggers>
</Configuration>

我(或多或少)知道我应该使用 LogManager,事实上我应该这样调用它:

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

或者,在 ma​​in() 中,可能像这样:

private static Logger LOGGER = null;

@BeforeClass
public static void setLogger() {
    System.setProperty("log4j.configurationFile","log4j.xml");
    LOGGER = LogManager.getLogger();
}

因为,我相信,使用 LogManager 我可以将日志指向 xml 文件以进行设置。 但是当我构建并运行它时,CLI 愤怒地在第一个日志中退出,报告:Exception in thread "main" java.lang.NullPointerException at myapp.modules.Database.<init>(Database.java:67)

预期结果: 我想要做的就是能够拥有我所有类(class)的日志,并将其写入文件。 我就是无法正常工作。当我不使用 LogManager 时,我只会在控制台上看到日志,但不会创建任何文件。 我同时使用 Windows 和 Linux(这就是/var/log/但我也将其更改为 C:\的原因)。

我用过的其他网站: https://howtodoinjava.com/log4j2/configure-log4j2-for-junit/

Log4J loggers for different classes <-- 没有帮助我

..许多其他搜索结果都超过 6 年了。

POM.xml:

<dependency>
    <groupId>org.apache.logging.log4j</groupId>
    <artifactId>log4j-api</artifactId>
    <version>2.10.0</version>
</dependency>
<dependency>
    <groupId>org.apache.logging.log4j</groupId>
    <artifactId>log4j-core</artifactId>
    <version>2.10.0</version>
</dependency>

最佳答案

您在几个层面上都错了:您将 JDK 的记录器与 Log4j2 的记录器混合在一起,您没有记录到多个附加程序,等等。

这是你应该做的:

/pom.xml

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.example</groupId>
    <artifactId>log4j2test</artifactId>
    <version>0.1</version>
    <packaging>jar</packaging>
    <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <maven.compiler.source>1.8</maven.compiler.source>
        <maven.compiler.target>1.8</maven.compiler.target>
    </properties>
    <dependencies>
        <dependency>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-api</artifactId>
            <version>2.10.0</version>
        </dependency>
        <dependency>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-core</artifactId>
            <version>2.10.0</version>
        </dependency>
    </dependencies>
</project>

这基本上是唯一没有错误的地方。

/src/main/java/so47656300/App.java

package so47656300;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

public class App {

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

  public static void main(String[] args) {
    logger.info("App.main - starting");
    new SecondClass();
    logger.info("App.main - ending");
  }
}

在这里,您的错误是使用 java.util.logger.Logger 而不是 org.apache.logging.log4j.Logger

/src/main/java/so47656300/SecondClass.java

package so47656300;

import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;

public class SecondClass {

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

  public SecondClass() {
    logger.info("SecondClass - starting");
    logger.info("SecondClass - ending");
  }
}

在这里,您的错误还在于使用了错误的 Logger 类。仅使用来自 org.apache.logging.log4j.* 的类。

/src/main/resources/log4j2.xml

<?xml version="1.0" encoding="UTF-8"?>
<Configuration status="WARN">
    <Properties>
        <Property name="basePath">/var/log</Property>
    </Properties>
    <Appenders>
        <RollingFile name="fileLogger" fileName="${basePath}/myApp.log" filePattern="${basePath}/myApp-%d{yyyy-MM-dd}.log">
            <PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n" />
            <Policies>
                <TimeBasedTriggeringPolicy interval="1" modulate="true" />
            </Policies>
        </RollingFile>

        <Console name="console" target="SYSTEM_OUT">
            <PatternLayout pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n" />
        </Console>
    </Appenders>
    <Loggers>
        <Root level="INFO">
            <AppenderRef ref="console"/>
            <AppenderRef ref="fileLogger"/>
        </Root>
    </Loggers>
</Configuration>

在这里,您的错误如下:

  1. 错误的文件名:Log4J 2 requires a name log4j2.xml .对于您的测试,创建一个文件 /src/test/resources/log4j2-test.xml
  2. 您只需要一个记录器,所以只使用一个:根记录器。您创建了多个,但您不需要它们。
  3. 将 appender 添加到记录器(Root-one)

输出

控制台

[INFO ] 2017-12-05 16:52:32.218 [main] App - App.main - starting
[INFO ] 2017-12-05 16:52:32.221 [main] SecondClass - SecondClass - starting
[INFO ] 2017-12-05 16:52:32.222 [main] SecondClass - SecondClass - ending
[INFO ] 2017-12-05 16:52:32.222 [main] App - App.main - ending

/var/log/myApp.log

[INFO ] 2017-12-05 16:52:32.218 [main] App - App.main - starting
[INFO ] 2017-12-05 16:52:32.221 [main] SecondClass - SecondClass - starting
[INFO ] 2017-12-05 16:52:32.222 [main] SecondClass - SecondClass - ending
[INFO ] 2017-12-05 16:52:32.222 [main] App - App.main - ending

关于java - 将 log4j2 用于多个类,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47656300/

相关文章:

java - Log4j在maven项目中登录

控制台应用程序中的 Java 键盘输入解析

java - 如何在 Maven 和 Intellij 之间处理 Junits 中的相对路径

Java 安全性从 SecretKeySpec 正确初始化 Cipher

java - Grails 2.0 为自己的类设置日志记录

java - 实现或替换公共(public)日志记录

java - 在运行时更新 JTree 节点背景颜色

java - 如何使用 CRUDRepository 保存列表但最后提交

java - 使用 Log4J 连接远程服务器进行日志记录

log4j - 使用 jboss-as-7.1.1 配置 log4j