我需要将Jersey请求/响应日志重定向到我的log4j2。
我在ApplicationJAXRS extends Application
上使用此代码启用了Jersey记录:
@Override
public Set<Class<?>> getClasses() {
return new HashSet<Class<?>>() {{
add(LoggingFilter.class);
}};
}
Jersey似乎在内部使用JUL(Java Logging),默认输出是STDOUT。此时我可以在Eclipse控制台上看到STDOUT。
Log4j2文档有一个关于JDK Logging Adapter的部分。 它说
要使用JDK日志记录适配器,必须将系统属性 java.util.logging.manager 设置为 org.apache.logging.log4j.jul.LogManager < / p>
这必须通过命令行(即使用-Djava.util.logging.manager = org.apache.logging.log4j.jul.LogManager参数)或使用 System.setProperty()来完成在对LogManager或Logger进行任何调用之前。
要在任何记录器呼叫之前呼叫System.setProperty(*)
,我已尝试将其放在@PostConstruct
课程的Aplication
上。
@PostConstruct
public void init() {
System.setProperty("java.util.logging.manager", "org.apache.logging.log4j.jul.LogManager");
}
我可以让它登录我的日志文件。
这是我的log4j2.xml:
<Appenders>
<RollingFile name="RollingFile" fileName="${log-path}/${name}.log"
filePattern="${log-path}/${date:yyyy-MM}/${name}-%d{yyyy-MM-dd}-%i.log">
<PatternLayout>
<Pattern>%d{dd-MM-yy HH:mm:ss,SSS} %-5p [%t] (%F:%L) - %m%n</Pattern>
</PatternLayout>
<Policies>
<TimeBasedTriggeringPolicy interval="1" modulate="true"/>
</Policies>
<DefaultRolloverStrategy max="10" />
</RollingFile>
<Console name="Console" target="SYSTEM_OUT">
<PatternLayout pattern="%d %-5p [%t] %C{2} (%F:%L) - %m%n" />
</Console>
</Appenders>
<Loggers>
<Root level="debug">
<AppenderRef ref="Console" level="debug"/>
<AppenderRef ref="RollingFile" level="debug"/>
</Root>
</Loggers>
</Configuration>
答案 0 :(得分:2)
我想你必须设置system property at launch。将代码添加到init方法以查看是否设置了系统属性。
@PostConstruct
public void init() {
String cn = "org.apache.logging.log4j.jul.LogManager";
System.setProperty("java.util.logging.manager", cn);
LogManager lm = LogManager.getLogManager();
if (!cn.equals(lm.getClass().getName())) {
try {
ClassLoader.getSystemClassLoader().loadClass(cn);
} catch (ClassNotFoundException cnfe) {
throw new IllegalStateException("Jars not in system class path.", cnfe);
}
throw new IllegalStateException("Found " + lm.getClass().getName() + " set as launch param instead.");
}
}
答案 1 :(得分:2)
这实际上适用于Jersey案例,但您仍然需要设置System属性java.util.logging.manager = org.apache.logging.log4j.jul.LogManager
对于常规应用程序日志记录,log4j2正常实例化您的记录器。然后,使用org.apache.logging.log4j.jul.LogManager显式实例化java.util.logging.Logger。然后,第二个Logger实例用于注册新的LoggingFilter,如此处所示,使用Jersey 2 Client作为此示例(为了清晰起见,详细命名):
org.apache.logging.log4j.Logger logger = org.apache.logging.log4j.LogManager.getLogger(this.getClass().getName());
java.util.logging.Logger jerseyLogger = org.apache.logging.log4j.jul.LogManager.getLogManager().getLogger(this.getClass().getName());
jerseyLogger.setLevel(java.util.logging.Level.SEVERE); //OPTIONAL
Client client = ClientBuilder.newClient();
client.register(new LoggingFilter(jerseyLogger, false));
logger.info("App logging uses the normal logger");
现在,对记录器的调用按预期工作,并且所有Jersey的jul日志记录输出都按预期返回到log4j2 appender。