我正在使用logback,我正在尝试以编程方式在我的Java程序中设置日志文件名(类似于Setting Logback Appender path programmatically),我尝试按如下方式调整该解决方案:
在logback-test.xml中:
<appender name="FILE" class="ch.qos.logback.core.FileAppender">
<file>log/${log_file_name}.log</file>
...
然后又在我的Java程序中:
String logFileName = "" + System.currentTimeMillis(); // just for example
System.setProperty("log_file_name", logFileName);
LoggerContext lc = (LoggerContext) LoggerFactory.getILoggerFactory();
ContextInitializer ci = new ContextInitializer(lc);
lc.reset();
try
{
// I prefer autoConfig() over JoranConfigurator.doConfigure() so I
// wouldn't need to find the file myself.
ci.autoConfig();
}
catch (JoranException e)
{
// StatusPrinter will try to log this
e.printStackTrace();
}
StatusPrinter.printInCaseOfErrorsOrWarnings(lc);
然而,结果是两个日志,一个完整并按我想要的名称命名,例如“1319041145343.log”,另一个是空的并命名为“log_file_name_IS_UNDEFINED.log”。如何阻止创建其他空日志文件?
答案 0 :(得分:33)
我相信以下内容更接近你想要的东西。
import ch.qos.logback.classic.Logger;
import ch.qos.logback.classic.encoder.PatternLayoutEncoder;
import ch.qos.logback.core.FileAppender;
import ch.qos.logback.core.util.StatusPrinter;
import org.slf4j.LoggerFactory;
import ch.qos.logback.classic.LoggerContext;
public class Main {
public static void main(String[] args) {
LoggerContext loggerContext = (LoggerContext) LoggerFactory.getILoggerFactory();
FileAppender fileAppender = new FileAppender();
fileAppender.setContext(loggerContext);
fileAppender.setName("timestamp");
// set the file name
fileAppender.setFile("log/" + System.currentTimeMillis()+".log");
PatternLayoutEncoder encoder = new PatternLayoutEncoder();
encoder.setContext(loggerContext);
encoder.setPattern("%r %thread %level - %msg%n");
encoder.start();
fileAppender.setEncoder(encoder);
fileAppender.start();
// attach the rolling file appender to the logger of your choice
Logger logbackLogger = loggerContext.getLogger("Main");
logbackLogger.addAppender(fileAppender);
// OPTIONAL: print logback internal status messages
StatusPrinter.print(loggerContext);
// log something
logbackLogger.debug("hello");
}
}
如果您只需要添加日志文件名的时间戳,则已经supports the timestamp element进行了回溯。因此,您实际上根本不需要任何自定义代码。
答案 1 :(得分:12)
要根据运行时属性将日志消息分离/筛选到不同的文件,您可能需要使用ch.qos.logback.classic.sift.SiftingAppender。
简而言之,这允许您设置FileAppender
(或任何其他appender)<file>${userid}.log</file>
,${userId}
根据MDC (Mapped Diagnostic Context)替换MDC.put("userid", "Alice");
(例如, {{1}})。请参阅完整示例的第一个链接。
答案 2 :(得分:8)
您可以执行以下操作来忽略那些额外的文件创建。下面是配置文件
<configuration>
<appender name="FILE" class="ch.qos.logback.core.FileAppender">
<!-- "application-name" is a variable -->
<File>c:/logs/${application-name}.log</File>
<layout class="ch.qos.logback.classic.PatternLayout">
<Pattern>%d %p %t %c - %m%n</Pattern>
</layout>
</appender>
<root level="debug">
<appender-ref ref="FILE"/>
</root>
</configuration>
这是java部分,
LoggerContext context = (LoggerContext) LoggerFactory.getILoggerFactory();
JoranConfigurator jc = new JoranConfigurator();
jc.setContext(context);
context.reset(); // override default configuration
// inject the name of the current application as "application-name"
// property of the LoggerContext
context.putProperty("application-name", NAME_OF_CURRENT_APPLICATION);
jc.doConfigure("/path/to/the/above/configuration/file.xml");
答案 3 :(得分:5)
看起来记录器已初始化两次。第一次,可能在应用加载时无法解析${log_file_name}
。如果您使用-Dlog_file_name=*something*
启动应用,则可以验证此行为,如果它创建了另一个名为*something*
的日志文件