I am doing the upgrade work from log4j1.2.17 to log4j2.12.0. I need to implement the features what we has done with log4j1.x. However, I'm having some tough problems:
In log4j1.x, after extends class
FileAppender
, I can useorg.apache.log4j.FileAppender#setFile
to modify the current output file. How to setFile in log4j2 ?In log4j1.x, by
org.apache.log4j.xml.DOMConfigurator#doConfigure
I can do the configuration incrementally. How to do that in log4j2 ? The scenario as follow : Firstly, I built the basic log4j2 configuration (logger apper layout) wit API. Then I want to use the file log4j2-new.xml to update the configuration incrementally based on the previous configuration.
update:
For the question2, the backgroung is as following:
I configure the basic logging system with a few XML. However, there is another module called reportService needs to programmatically create some loggers to write report data to files. The basic logging system needs to support hot deployment, which means that the logger needs to be refreshed when the xml changes without removing the loggers create by reportService. I have read the manual of log4j2. And I tried CompositeConfiguration
, but It seems the class can't take the config from ((LoggerContext) LogManager.getContext(false)).getConfiguration()
as parameter. I think the reason is CompositeConfiguration can't use config that has called initialize()
. Here is a example (I use log4j2-base.xml to simulate creating loggers programmatically )
public class LoadXmlConfigurationTest {
public static final String BASE_CONFIG = "log4j2-base.xml";
public static final String EXT_CONFIG = "log4j2-ext.xml";
@Test
public void loadXmlConfigTest() {
System.setProperty(ConfigurationFactory.CONFIGURATION_FILE_PROPERTY, BASE_CONFIG);
Configuration baseConfig = ((LoggerContext) LogManager.getContext(false)).getConfiguration();
final Configuration extConfig = loadConfiguration("log4j2-ext.xml");
List<AbstractConfiguration> configs = new ArrayList<>();
configs.add((AbstractConfiguration) baseConfig);
configs.add((AbstractConfiguration) extConfig);
CompositeConfiguration compositeConfiguration = new CompositeConfiguration(configs);
((LoggerContext) LogManager.getContext(false)).reconfigure(compositeConfiguration);
Logger logger = LogManager.getLogger("EXT");
Logger rootLogger = LogManager.getRootLogger();
logger.error("ext logger info");
rootLogger.error("root logger info");
}
private Configuration loadConfiguration(final String resourcePath) {
try (final InputStream in = getClass().getClassLoader().getResourceAsStream(resourcePath)) {
return new XmlConfiguration(new LoggerContext("test"), new ConfigurationSource(in));
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
}
output is as follow, the baseConfig doesn't work:
2020-03-01 10:26:41,394 main ERROR No logging configuration
EXT | 2020-03-01 10:26:41,411 ERROR [main] (LoadXmlConfigurationTest.java:50) - ext logger info
10:26:41.413 [main] ERROR - root logger info
log4j2-base.xml
<?xml version="1.0" encoding="UTF-8"?>
<Configuration>
<Appenders>
<Console name="ROOT" target="SYSTEM_OUT">
<PatternLayout>
<pattern>ROOT | %d %-5p [%t] %C{2} (%F:%L) - %m%n</pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Root level="debug">
<AppenderRef ref="ROOT" />
</Root>
</Loggers>
</Configuration>
log4j2-ext.xml
log4j
<?xml version="1.0" encoding="UTF-8"?>
<Configuration>
<Appenders>
<Console name="EXT" target="SYSTEM_OUT">
<PatternLayout>
<pattern>EXT | %d %-5p [%t] (%F:%L) - %m%n</pattern>
</PatternLayout>
</Console>
</Appenders>
<Loggers>
<Logger name="EXT" level="DEBUG" additivity="false">
<AppenderRef ref="EXT" />
</Logger>
</Loggers>
</Configuration>