我正在将1.x版本的log4j产品升级到2.5
我们有一个属性文件,其中包含各种配置。示例配置(trace.properties)如下:
cfg_test.status=debug
cfg_test.appenders=rolling
cfg_test.appender.rolling.type=RollingFile
cfg_test.appender.rolling.name=RollingFile_TEST
cfg_test.appender.rolling.fileName=D:/log/test.log
cfg_test.appender.rolling.filePattern=D:/log/test_%d{MMdd}.log
cfg_test.appender.rolling.layout.type=PatternLayout
cfg_test.appender.rolling.layout.pattern=%d %-5p %m%n
cfg_test.appender.rolling.policies.type = Policies
cfg_test.appender.rolling.policies.time.type = TimeBasedTriggeringPolicy
cfg_test.appender.rolling.policies.time.interval = 1
cfg_test.appender.rolling.policies.time.modulate = true
cfg_test.appender.rolling.policies.size.type = SizeBasedTriggeringPolicy
cfg_test.appender.rolling.policies.size.size=100MB
cfg_test.appender.rolling.strategy.type = DefaultRolloverStrategy
cfg_test.appender.rolling.strategy.max = 5
cfg_test.rootLogger.level=debug
cfg_test.rootLogger.appenderRefs=test
cfg_test.rootLogger.appenderRef.test.ref=RollingFile_TEST
cfg_crp.rootLogger.level=info
cfg_crp.rootLogger.appenderRefs=crp, stdout
cfg_crp.rootLogger.appenderRef.crp.ref=RollingFile_CRP
cfg_crp.rootLogger.appenderRef.stdout.ref=STDOUT
此处cfg_test是测试配置,cfg_crp是产品功能的配置,作为单独的模块启动。
我有一个自定义工厂,如下所示:
public class TraceFactory {
private static boolean isInitialized = false;
/**
* intializes the trace with the given trace key.
* <p/>
* If if the trace key is null, we will use the console trace
*
* @param traceKey trace key
*/
public static void initialize(String traceKey) {
initPrefix(traceKey != null ? "cfg_" + traceKey + "." : null, PropertiesUtils.readFromClassPath("properties/trace"));
}
private static void initPrefix(String prefix, Properties properties) {
if (isInitialized) {
return;
}
if (prefix == null) {
TraceFactory.initializeAsConsoleTracer();
return;
}
Properties cfg = new Properties();
for (Map.Entry<Object, Object> objectObjectEntry : properties.entrySet()) {
Map.Entry entry = (Map.Entry) objectObjectEntry;
String key = (String) entry.getKey();
String value = (String) entry.getValue();
if (key.startsWith(prefix)) {
cfg.put(key.substring(prefix.length()), value);
}
}
PropertiesConfigurationFactory factory = new PropertiesConfigurationFactory(); // This line and the try catch below replace the
try {
ConfigurationSource configSrc = createConfigurationSource(cfg); //PropertyConfigurator.configure(cfg); from log4j1.2
Configuration conf = factory.getConfiguration(configSrc);
LoggerContext ctx = Configurator.initialize(conf);
ctx.reconfigure();
}
catch (IOException io)
{
}
isInitialized = true;
}
/**
*
* @param cfg the log4j configuration as a properties bundle read from a properties file.
* @return {@link ConfigurationSource} object
* @throws IOException
*/
private static ConfigurationSource createConfigurationSource(Properties cfg) throws IOException {
ByteArrayOutputStream out = new ByteArrayOutputStream();
cfg.store(out, null);
InputStream in = new ByteArrayInputStream(out.toByteArray());
return new ConfigurationSource(in);
}
public static TraceInterface getTracer(Class class_) {
if (useConsoleTracer) {
return new ConsoleTracer(null);
}
return Log4JTracer.getTracer(class_);
}
public static TraceInterface getTracer(String name) {
if (useConsoleTracer) {
return new ConsoleTracer(null);
}
return Log4JTracer.getTracer(name);
}
}
我的LogWrapper Log4JTracer是: -
public class Log4JTracer implements TraceInterface {
private static final String FQCN = Log4JTracer.class.getName();
/**
* extended logger wrapper
*/
private final ExtendedLoggerWrapper log;
private Log4JTracer(final Logger logger) {
this.log = new ExtendedLoggerWrapper((AbstractLogger)logger, logger.getName(), logger.getMessageFactory());
}
/**
* Constructs new logger.
*
* @param name internally used by log4j.
*/
protected Log4JTracer(String name) {
Logger logger = LogManager.getLogger(name);
log = new ExtendedLoggerWrapper((ExtendedLogger) logger, logger.getName(), logger.getMessageFactory());
}
/**
*
* @param clazz
*/
public Log4JTracer(Class<?> clazz)
{
Logger logger = LogManager.getLogger(clazz);
log = new ExtendedLoggerWrapper((ExtendedLogger) logger, logger.getName(), logger.getMessageFactory());
}
/**
* {@inheritDoc}
*/
public void debug(Object message) {
debug(message, null);
}
/**
* {@inheritDoc}
*/
public void debug(Object message, Throwable t) {
log.logIfEnabled(FQCN, Level.DEBUG, null, message, t);
}
/**
* {@inheritDoc}
*/
public void info(Object message) {
info(message, null);
}
/**
* {@inheritDoc}
*/
public void info(Object message, Throwable t) {
log.logIfEnabled(FQCN, Level.INFO, null, message, t);
}
/**
* {@inheritDoc}
*/
public boolean isWarnEnabled() {
return log.isWarnEnabled();
}
/**
* {@inheritDoc}
*/
public void warn(Object message) {
warn(message, null);
}
/**
* {@inheritDoc}
*/
public void warn(Object message, Throwable t) {
log.logIfEnabled(FQCN, Level.WARN, null, message, t);
}
/**
* {@inheritDoc}
*/
public boolean isErrorEnabled() {
return log.isErrorEnabled();
}
/**
* {@inheritDoc}
*/
public void error(Object message) {
error(message, null);
}
/**
* {@inheritDoc}
*/
public void error(Object message, Throwable t) {
log.logIfEnabled(FQCN, Level.ERROR, null, message, t);
}
/**
* {@inheritDoc}
*/
public boolean isFatalEnabled() {
return log.isFatalEnabled();
}
/**
* {@inheritDoc}
*/
public void fatal(Object message, Throwable t) {
log.logIfEnabled(FQCN, Level.FATAL, null, message, t);
}
/**
* {@inheritDoc}
*/
@Override
public boolean isDebugEnabled() {
return log.isDebugEnabled();
}
/**
* {@inheritDoc}
*/
@Override
public boolean isInfoEnabled() {
return log.isInfoEnabled();
}
public static Log4JTracer getTracer(Class cl) {
return new Log4JTracer(cl);
}
public static Log4JTracer getTracer(String name) {
return new Log4JTracer(name);
}
}
现在,当我尝试使用类中的记录器时,它根据配置没有得到记录器:
Public class Test {
Private TraceInterface trace;
Public void execute() {
TraceFactory.initialize("test");
trace = TraceFactory.getTracer();
trace.debug("testing.."); // this never prints. Although a test.log is created with zero size as soon as the TraceFactory.initialize method finshes.
谢谢和问候,
塔伦
答案 0 :(得分:0)
我通过以下方式开展工作:
将TraceFactory修改为:
private LoggerContext ctx;
..... 在方法initPrefix
中//ctx.reconfigure();
ctx.start(conf);
ContextAnchor.THREAD_CONTEXT.set(ctx);
ctx.updateLoggers();