BAEL-1338 - Programmatic Log4j2

This commit features a number of tests for programmatically configuring log4j.

Note that in order to have these tests live together, there is a slight deviation in how
these are configured vs how they are in the real world, specifically around static initialization.

Generally speaking, whenever static initialization is needed for a given configuration,
it is embedded in a @BeforeClass-annotated JUnit method.

Also, to isolate the tests from each other's plugins, annotation processing was turned off
in the build. This is not required when doing programmatic configuration of log4j. It is simply
needed for the specific use case of demonstrating these various log4j plugins all in the
same module.
This commit is contained in:
Josh Cummings 2018-05-19 22:07:54 -06:00 committed by GitHub
parent 8820ebb00f
commit ba55cfb67d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
25 changed files with 181 additions and 390 deletions

View File

@ -1,19 +0,0 @@
<?xml version="1.0"?>
<project
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"
xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>log4j2-programmatic-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>modify-xml-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
<name>modify-xml-configuration</name>
<url>http://maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
</project>

View File

@ -1,29 +0,0 @@
/**
This class demonstrates on modifying the loaded xml configuration by
extending XMLConfigurationFactory as defined in section 4.4 of
"Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.config;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.ConfigurationFactory;
import org.apache.logging.log4j.core.config.ConfigurationSource;
import org.apache.logging.log4j.core.config.Order;
import org.apache.logging.log4j.core.config.plugins.Plugin;
import org.apache.logging.log4j.core.config.xml.XmlConfigurationFactory;
@Plugin(name = "CustomConfigurationFactory", category = ConfigurationFactory.CATEGORY)
@Order(50)
public class CustomXMLConfigurationFactory extends XmlConfigurationFactory {
@Override
public Configuration getConfiguration(LoggerContext loggerContext, ConfigurationSource source) {
return new MyXMLConfiguration(loggerContext, source);
}
@Override
public String[] getSupportedTypes() {
return new String[] { ".xml", "*" };
}
}

View File

@ -1,35 +0,0 @@
/**
This class demonstrates on overriding the configuration loaded through xml
as defined in section 4.4 of "Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.config;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.Layout;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.appender.FileAppender;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.ConfigurationSource;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.logging.log4j.core.config.xml.XmlConfiguration;
import org.apache.logging.log4j.core.layout.PatternLayout;
public class MyXMLConfiguration extends XmlConfiguration {
public MyXMLConfiguration(LoggerContext loggerContext, ConfigurationSource source) {
super(loggerContext, source);
}
@Override
protected void doConfigure() {
super.doConfigure();
final LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
Configuration config = ctx.getConfiguration();
LoggerConfig loggerConfig = config.getLoggerConfig("com");
final Layout layout = PatternLayout.createLayout("[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n", null, config, null, null, false, false, null, null);
Appender appender = FileAppender.createAppender("target/test.log", "false", "false", "File", "true", "false", "false", "4000", layout, null, "false", null, config);
loggerConfig.addAppender(appender, Level.DEBUG, null);
addAppender(appender);
}
}

View File

@ -1,17 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<Configuration monitorInterval="60">
<Appenders>
<Console name="console" target="SYSTEM_OUT">
<PatternLayout
pattern="[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n" />
</Console>
</Appenders>
<Loggers>
<Logger name="com" additivity="false" level="info">
<AppenderRef ref="console" />
</Logger>
<Root>
<AppenderRef ref="console" />
</Root>
</Loggers>
</Configuration>

View File

@ -1,23 +0,0 @@
package com.baeldung.log4j2.logtest;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.plugins.util.PluginManager;
import org.junit.Test;
public class LogTest {
static{
PluginManager.addPackage("com.baeldung.log4j2.config");
}
@Test
public void simpleProgrammaticConfiguration() {
Logger logger = LogManager.getLogger();
LoggerContext ctx = (LoggerContext) LogManager.getContext();
logger.debug("Debug log message");
logger.info("Info log message");
logger.error("Error log message");
}
}

View File

@ -1,34 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>log4j2-programmatic-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
<packaging>pom</packaging>
<modules>
<module>simple-configuration</module>
<module>set-configuration-factory</module>
<module>simple-configurator</module>
<module>simple-configuration-xml</module>
<module>modify-xml-configuration</module>
</modules>
<dependencies>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.12</version>
<scope>test</scope>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-core</artifactId>
<version>2.11.0</version>
</dependency>
<dependency>
<groupId>org.apache.logging.log4j</groupId>
<artifactId>log4j-slf4j-impl</artifactId>
<version>2.11.0</version>
</dependency>
</dependencies>
</project>

View File

@ -1,10 +0,0 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>log4j2-programmatic-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>set-configuration-factory</artifactId>
</project>

View File

@ -1,88 +0,0 @@
/**
This class demonstrates how to build the components of
the configuration factory, as described in Section 3 of
"Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.config;
import java.io.IOException;
import java.net.URI;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.core.Filter;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.ConfigurationFactory;
import org.apache.logging.log4j.core.config.ConfigurationSource;
import org.apache.logging.log4j.core.config.builder.api.AppenderComponentBuilder;
import org.apache.logging.log4j.core.config.builder.api.ComponentBuilder;
import org.apache.logging.log4j.core.config.builder.api.ConfigurationBuilder;
import org.apache.logging.log4j.core.config.builder.api.FilterComponentBuilder;
import org.apache.logging.log4j.core.config.builder.api.LayoutComponentBuilder;
import org.apache.logging.log4j.core.config.builder.api.LoggerComponentBuilder;
import org.apache.logging.log4j.core.config.builder.api.RootLoggerComponentBuilder;
import org.apache.logging.log4j.core.config.builder.impl.BuiltConfiguration;
public class CustomConfigurationFactory extends ConfigurationFactory {
static Configuration createConfiguration(final String name, ConfigurationBuilder<BuiltConfiguration> builder) {
AppenderComponentBuilder console = builder.newAppender("Stdout", "Console");
LayoutComponentBuilder layout = builder.newLayout("PatternLayout")
.addAttribute("pattern", "%d [%t] %-5level: %msg%n%throwable");
console.add(layout);
FilterComponentBuilder filter = builder.newFilter("MarkerFilter", Filter.Result.ACCEPT, Filter.Result.DENY);
filter.addAttribute("marker", "FLOW");
console.add(filter);
builder.add(console);
ComponentBuilder triggeringPolicies = builder.newComponent("Policies")
.addComponent(builder.newComponent("CronTriggeringPolicy")
.addAttribute("schedule", "0 0 0 * * ?"))
.addComponent(builder.newComponent("SizeBasedTriggeringPolicy")
.addAttribute("size", "100M"));
AppenderComponentBuilder rollingFile = builder.newAppender("rolling", "RollingFile");
rollingFile.addAttribute("fileName", "target/rolling.log");
rollingFile.addAttribute("filePattern", "target/archive/rolling-%d{MM-dd-yy}.log.gz");
rollingFile.add(layout);
rollingFile.addComponent(triggeringPolicies);
builder.add(rollingFile);
AppenderComponentBuilder file = builder.newAppender("FileSystem", "File");
file.addAttribute("fileName", "target/logging.log");
file.add(layout);
builder.add(file);
LoggerComponentBuilder logger = builder.newLogger("com", Level.DEBUG);
logger.add(builder.newAppenderRef("Stdout"));
logger.add(builder.newAppenderRef("rolling"));
logger.add(builder.newAppenderRef("FileSystem"));
logger.addAttribute("additivity", false);
builder.add(logger);
RootLoggerComponentBuilder rootLogger = builder.newRootLogger(Level.ERROR);
rootLogger.add(builder.newAppenderRef("Stdout"));
rootLogger.add(builder.newAppenderRef("rolling"));
rootLogger.add(builder.newAppenderRef("FileSystem"));
rootLogger.addAttribute("additivity", false);
builder.add(rootLogger);
try {
builder.writeXmlConfiguration(System.out);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return builder.build();
}
public Configuration getConfiguration(final LoggerContext loggerContext, final String name, final URI configLocation) {
ConfigurationBuilder<BuiltConfiguration> builder = newConfigurationBuilder();
return createConfiguration(name, builder);
}
@Override
protected String[] getSupportedTypes() {
return new String[] { "*" };
}
@Override
public Configuration getConfiguration(LoggerContext loggerContext, ConfigurationSource source) {
return getConfiguration(loggerContext, source.toString(), null);
}
}

View File

@ -1,17 +0,0 @@
<?xml version="1.0"?>
<project
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"
xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>log4j2-programmatic-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>simple-configuration-xml</artifactId>
<name>simple-configuration-xml</name>
<url>http://maven.apache.org</url>
<properties>
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
</properties>
</project>

View File

@ -1,32 +0,0 @@
<?xml version="1.0" ?>
<Configuration>
<Appenders>
<Console name="Stdout">
<PatternLayout pattern="%d [%t] %-5level: %msg%n%throwable" />
<MarkerFilter onMatch="ACCEPT" onMismatch="DENY" marker="FLOW" />
</Console>
<RollingFile name="rolling" fileName="target/rolling.log"
filePattern="target/archive/rolling-%d{MM-dd-yy}.log.gz">
<PatternLayout pattern="%d [%t] %-5level: %msg%n%throwable" />
<Policies>
<CronTriggeringPolicy schedule="0 0 0 * * ?" />
<SizeBasedTriggeringPolicy size="100M" />
</Policies>
</RollingFile>
<File name="FileSystem" fileName="target/logging.log">
<PatternLayout pattern="%d [%t] %-5level: %msg%n%throwable" />
</File>
</Appenders>
<Loggers>
<Logger name="com" level="DEBUG" additivity="false">
<AppenderRef ref="Stdout" />
<AppenderRef ref="rolling" />
<AppenderRef ref="FileSystem" />
</Logger>
<Root level="ERROR" additivity="false">
<AppenderRef ref="Stdout" />
<AppenderRef ref="rolling" />
<AppenderRef ref="FileSystem" />
</Root>
</Loggers>
</Configuration>

View File

@ -1,30 +0,0 @@
/**
This class loads the logging configuration from the xml defined in
src/main/resources and uses the same configuration generated through
programmatic configuration as defined in simple-configuration example.
**/
package com.baeldung.log4j2.logtest;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.MarkerManager;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
@RunWith(JUnit4.class)
public class LogTest {
@Test
public void simpleProgrammaticConfiguration(){
Logger logger = LogManager.getLogger();
Marker markerContent = MarkerManager.getMarker("FLOW");
logger.debug(markerContent, "Debug log message");
logger.info(markerContent, "Info log message");
logger.error(markerContent, "Error log message");
}
}

View File

@ -1,10 +0,0 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>log4j2-programmatic-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>simple-configuration</artifactId>
</project>

View File

@ -1,10 +0,0 @@
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
<modelVersion>4.0.0</modelVersion>
<parent>
<groupId>com.baeldung.log4j2</groupId>
<artifactId>log4j2-programmatic-configuration</artifactId>
<version>0.0.1-SNAPSHOT</version>
</parent>
<artifactId>simple-configurator</artifactId>
</project>

View File

@ -53,13 +53,25 @@
<type>test-jar</type>
<scope>test</scope>
</dependency>
</dependencies>
</dependencies>
<properties>
<jackson.version>2.9.3</jackson.version>
<jackson.version>2.9.5</jackson.version>
<h2.version>1.4.193</h2.version>
<commons-dbcp2.version>2.1.1</commons-dbcp2.version>
<log4j-core.version>2.10.0</log4j-core.version>
<log4j-core.version>2.11.0</log4j-core.version>
</properties>
<build>
<plugins>
<plugin>
<groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-compiler-plugin</artifactId>
<version>3.7.0</version>
<configuration>
<proc>none</proc>
</configuration>
</plugin>
</plugins>
</build>
</project>

View File

@ -0,0 +1,18 @@
package com.baeldung.logging.log4j2;
import org.apache.logging.log4j.core.config.ConfigurationFactory;
import org.apache.logging.log4j.spi.LoggerContextFactory;
import org.junit.AfterClass;
import java.lang.reflect.Field;
public class Log4j2Test {
@AfterClass
public static void tearDown() throws Exception {
Field factories = ConfigurationFactory.class.getDeclaredField("factories");
factories.setAccessible(true);
factories.set(null, null);
ConfigurationFactory.resetConfigurationFactory();
}
}

View File

@ -2,32 +2,34 @@
This class invokes the configuration factory with static initialization,
as defined in section 4.1 of the "Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.logtest;
package com.baeldung.logging.log4j2.setconfigurationfactory;
import com.baeldung.logging.log4j2.Log4j2Test;
import com.baeldung.logging.log4j2.simpleconfiguration.CustomConfigurationFactory;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.MarkerManager;
import org.apache.logging.log4j.core.config.ConfigurationFactory;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
import com.baeldung.log4j2.config.CustomConfigurationFactory;
@RunWith(JUnit4.class)
public class LogTest {
static {
public class SetConfigurationFactoryTest extends Log4j2Test {
@BeforeClass
public static void setUp() {
CustomConfigurationFactory customConfigurationFactory = new CustomConfigurationFactory();
ConfigurationFactory.setConfigurationFactory(customConfigurationFactory);
}
@Test
public void simpleProgrammaticConfiguration() {
Logger logger = LogManager.getLogger();
public void givenDirectConfiguration_whenUsingFlowMarkers_ThenLogsCorrectly() {
Logger logger = LogManager.getLogger(this.getClass());
Marker markerContent = MarkerManager.getMarker("FLOW");
logger.debug(markerContent, "Debug log message");
logger.info(markerContent, "Info log message");
logger.error(markerContent, "Error log message");
}
}
}

View File

@ -3,8 +3,7 @@
the configuration factory, as described in Section 3 of
"Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.config;
package com.baeldung.logging.log4j2.simpleconfiguration;
import java.io.IOException;
import java.net.URI;
@ -26,7 +25,7 @@ import org.apache.logging.log4j.core.config.builder.api.RootLoggerComponentBuild
import org.apache.logging.log4j.core.config.builder.impl.BuiltConfiguration;
import org.apache.logging.log4j.core.config.plugins.Plugin;
@Plugin(name = "CustomConfigurationFactory", category = ConfigurationFactory.CATEGORY)
@Plugin(name = "simple", category = ConfigurationFactory.CATEGORY)
@Order(50)
public class CustomConfigurationFactory extends ConfigurationFactory {
@ -92,3 +91,4 @@ public class CustomConfigurationFactory extends ConfigurationFactory {
return new String[] { "*" };
}
}

View File

@ -2,21 +2,29 @@
This class invokes the configuration factory through the run time property,
as defined in section 4.2 of the "Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.logtest;
package com.baeldung.logging.log4j2.simpleconfiguration;
import com.baeldung.logging.log4j2.Log4j2Test;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.MarkerManager;
import org.apache.logging.log4j.core.config.plugins.util.PluginManager;
import org.junit.BeforeClass;
import org.junit.Test;
public class LogTest {
public class SimpleConfigurationTest extends Log4j2Test {
@BeforeClass
public static void setUp() {
PluginManager.addPackage("com.baeldung.logging.log4j2.simpleconfiguration");
}
@Test
public void simpleProgrammaticConfiguration() {
Logger logger = LogManager.getLogger();
public void givenSimpleConfigurationPlugin_whenUsingFlowMarkers_thenLogsCorrectly() throws Exception {
Logger logger = LogManager.getLogger(this.getClass());
Marker markerContent = MarkerManager.getMarker("FLOW");
logger.debug(markerContent, "Debug log message");
logger.info(markerContent, "Info log message");
logger.error(markerContent, "Error log message");
}
}
}

View File

@ -1,4 +1,5 @@
package com.baeldung.log4j2.logtest;
package com.baeldung.logging.log4j2.simpleconfigurator;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
@ -12,4 +13,4 @@ public class LogPrinter {
logger.info("Info log message");
logger.error("Error log message");
}
}
}

View File

@ -1,10 +1,11 @@
/**
This class demonstrates how to use ConfigurationBuilderFactory directly,
as described in Section 3 of "Programmatic Configuration with Log4j 2"
**/
* This class demonstrates how to use ConfigurationBuilderFactory directly,
* as described in Section 3 of "Programmatic Configuration with Log4j 2"
**/
package com.baeldung.log4j2.configure;
package com.baeldung.logging.log4j2.simpleconfigurator;
import com.baeldung.logging.log4j2.Log4j2Test;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.core.appender.ConsoleAppender;
import org.apache.logging.log4j.core.config.Configurator;
@ -16,23 +17,22 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.JUnit4;
import com.baeldung.log4j2.logtest.LogPrinter;
@RunWith(JUnit4.class)
public class LogTest {
public class SimpleConfiguratorTest extends Log4j2Test {
@Test
public void simpleProgrammaticConfiguration() {
public void givenDefaultLog4j2Environment_whenProgrammaticallyConfigured_thenLogsCorrectly() {
ConfigurationBuilder<BuiltConfiguration> builder = ConfigurationBuilderFactory.newConfigurationBuilder();
AppenderComponentBuilder console = builder.newAppender("Stdout", "CONSOLE")
.addAttribute("target", ConsoleAppender.Target.SYSTEM_OUT);
.addAttribute("target", ConsoleAppender.Target.SYSTEM_OUT);
console.add(builder.newLayout("PatternLayout")
.addAttribute("pattern", "%d [%t] %-5level: %msg%n%throwable"));
.addAttribute("pattern", "%d [%t] %-5level: %msg%n%throwable"));
builder.add(console);
builder.add(builder.newLogger("com", Level.DEBUG)
.add(builder.newAppenderRef("Stdout"))
.addAttribute("additivity", false));
.add(builder.newAppenderRef("Stdout"))
.addAttribute("additivity", false));
builder.add(builder.newRootLogger(Level.ERROR)
.add(builder.newAppenderRef("Stdout")));
.add(builder.newAppenderRef("Stdout")));
Configurator.initialize(builder.build());
LogPrinter logPrinter = new LogPrinter();
logPrinter.printlog();

View File

@ -6,6 +6,7 @@ import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.PrintStream;
import com.baeldung.logging.log4j2.Log4j2Test;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.junit.Before;
@ -13,7 +14,7 @@ import org.junit.Test;
import com.fasterxml.jackson.databind.ObjectMapper;
public class JSONLayoutTest {
public class JSONLayoutTest extends Log4j2Test {
private static Logger logger;
private ByteArrayOutputStream consoleOutput = new ByteArrayOutputStream();

View File

@ -0,0 +1,24 @@
package com.baeldung.logging.log4j2.xmlconfiguration;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.ConfigurationFactory;
import org.apache.logging.log4j.core.config.ConfigurationSource;
import org.apache.logging.log4j.core.config.Order;
import org.apache.logging.log4j.core.config.plugins.Plugin;
import org.apache.logging.log4j.core.config.xml.XmlConfigurationFactory;
@Plugin(name = "xml", category = ConfigurationFactory.CATEGORY)
@Order(50)
public class CustomXMLConfigurationFactory extends XmlConfigurationFactory {
@Override
public Configuration getConfiguration(LoggerContext loggerContext, ConfigurationSource source) {
return new MyXMLConfiguration(loggerContext, source);
}
@Override
public String[] getSupportedTypes() {
return new String[] { ".xml", "*" };
}
}

View File

@ -0,0 +1,36 @@
/**
This class demonstrates on overriding the configuration loaded through xml
as defined in section 4.4 of "Programmatic Configuration with Log4j 2"
**/
package com.baeldung.logging.log4j2.xmlconfiguration;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.Layout;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.appender.FileAppender;
import org.apache.logging.log4j.core.config.Configuration;
import org.apache.logging.log4j.core.config.ConfigurationSource;
import org.apache.logging.log4j.core.config.LoggerConfig;
import org.apache.logging.log4j.core.config.xml.XmlConfiguration;
import org.apache.logging.log4j.core.layout.PatternLayout;
public class MyXMLConfiguration extends XmlConfiguration {
public MyXMLConfiguration(LoggerContext loggerContext, ConfigurationSource source) {
super(loggerContext, source);
}
@Override
protected void doConfigure() {
super.doConfigure();
final LoggerContext ctx = (LoggerContext) LogManager.getContext(false);
Configuration config = ctx.getConfiguration();
LoggerConfig loggerConfig = config.getLoggerConfig("com");
final Layout layout = PatternLayout.createLayout("[%-5level] %d{yyyy-MM-dd HH:mm:ss.SSS} [%t] %c{1} - %msg%n", null, config, null, null, false, false, null, null);
Appender appender = FileAppender.createAppender("target/test.log", "false", "false", "File", "true", "false", "false", "4000", layout, null, "false", null, config);
loggerConfig.addAppender(appender, Level.DEBUG, null);
addAppender(appender);
}
}

View File

@ -0,0 +1,44 @@
/**
This class loads the logging configuration from the xml defined in
src/main/resources and uses the same configuration generated through
programmatic configuration as defined in simple-configuration example.
**/
package com.baeldung.logging.log4j2.xmlconfiguration;
import com.baeldung.logging.log4j2.Log4j2Test;
import org.apache.logging.log4j.LogManager;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.MarkerManager;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.core.config.plugins.util.PluginManager;
import org.junit.BeforeClass;
import org.junit.Test;
public class XMLConfigLogTest extends Log4j2Test {
@BeforeClass
public static void setUp() {
PluginManager.addPackage("com.baeldung.logging.log4j2.xmlconfiguration");
}
@Test
public void givenXMLConfigurationPlugin_whenUsingFlowMarkers_ThenLogsCorrectly() throws Exception {
Logger logger = LogManager.getLogger(this.getClass());
Marker markerContent = MarkerManager.getMarker("FLOW");
logger.debug(markerContent, "Debug log message");
logger.info(markerContent, "Info log message");
logger.error(markerContent, "Error log message");
}
@Test
public void givenXMLConfigurationPlugin_whenSimpleLog_ThenLogsCorrectly() throws Exception {
Logger logger = LogManager.getLogger(this.getClass());
LoggerContext ctx = (LoggerContext) LogManager.getContext();
logger.debug("Debug log message");
logger.info("Info log message");
logger.error("Error log message");
}
}

View File

@ -94,7 +94,6 @@
<module>logging-modules/log-mdc</module>
<module>logging-modules/log4j</module>
<module>logging-modules/log4j2</module>
<module>logging-modules/log4j2-programmatic-configuration</module>
<module>logging-modules/logback</module>
<module>lombok</module>
<module>mapstruct</module>