以编程方式从Log4j2 XML配置获取属性

时间:2017-05-23 18:37:04

标签: java log4j2

在我的Log4j2配置文件中,我有这个:

<?xml version="1.0" encoding="UTF-8"?>
<Configuration status="WARN" strict="true" name="XMLConfig" packages="org.apache.logging.log4j.test">
    <Properties>
        <Property name="baseDir">log-dir/</Property>
        <Property name="defaultLogfileName">default-log-file</Property>
    </Properties>

现在,在我的一些代码中,我创建了自定义记录器。我需要访问“baseDir”的值并进行更改。我尝试过使用上下文中的getProperties

LoggerContext context = (LoggerContext) LogManager.getContext(false);
Configuration configuration = context.getConfiguration();
configuration.getProperties();

但是返回的地图有“hostname”和“contextName”键。不是我正在寻找的属性地图。

我认为我可以从rootLogger中获取它:

LoggerContext context = (LoggerContext) LogManager.getContext(false);
Configuration configuration = context.getConfiguration()
for (Property p : configuration.getRootLogger().getPropertyList())
{
    ...
}

但是这会产生NullPointerException,因为getPropertyList返回null。

那么,如何使用名称“baseDir”访问该属性,以便我可以以编程方式创建一个新的记录器,但具有不同的基本目录?

1 个答案:

答案 0 :(得分:2)

context.getConfiguration()返回的类 Configuration 不是一种 PropertyConfiguration 类。它不能用于访问log4j2.xml值,因为它是针对日志记录设置而定制的非常不同的 Configuration 类。

可以将 baseDir 定义提取到单独的属性文件中。这为编程和非编程log4j配置提供了通用源:以编程方式,它可以作为常规属性配置文件进行访问; log4j2配置可以作为属性查找来访问它。

这看起来像这样:

  1. 外部属性文件logsCommons.properties与log4j2.xml位于同一文件夹中,并具有以下属性:

    baseDir=log-dir
    
  2. log4j2xml定义如下:

    <Properties>
        <Property name="baseDir">${bundle:logsCommons:baseDir}/</Property>
        <Property name="defaultLogfileName">default-log-file</Property>
    </Properties>
    
  3. 来自OP:

    除了将baseDir的值移动到属性文件并如上所述引用它${bundle:logsCommon:baseDir}之外,我这样做是为了得到我的实际解决方案:

    获取StrSubstitutor:

    String baseDirVar = configuration.getStrSubstitutor().getVariableResolver().look‌​up("baseDir"); 
    

    然后我需要做一个替换:

    String baseDir = configuration.getStrSubstitutor().replace(baseDirVar);
    

    现在我可以可靠地获取(并在必要时修改)用于记录的基本目录,该目录现在来自属性文件。