Author: rgoers
Date: Mon Oct 22 01:15:34 2012
New Revision: 1400744
URL: http://svn.apache.org/viewvc?rev=1400744&view=rev
Log:
LOG4J2-28 - Added PropertiesRewritePolicy and ability to add properties to a
Logger.
Added:
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/PropertiesRewritePolicy.java
- copied, changed from r1400243,
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/MapRewritePolicy.java
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLLoggerPropsTest.java
- copied, changed from r1397892,
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLConfigurationPropsTest.java
logging/log4j/log4j2/trunk/core/src/test/resources/log4j-loggerprops.xml
- copied, changed from r1397892,
logging/log4j/log4j2/trunk/core/src/test/resources/log4j-props.xml
Modified:
logging/log4j/log4j2/trunk/api/src/main/java/org/apache/logging/log4j/ThreadContext.java
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/config/LoggerConfig.java
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/Log4jLogEvent.java
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/LogEventFactory.java
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/appender/rewrite/RewriteAppenderTest.java
logging/log4j/log4j2/trunk/core/src/test/resources/log4j-rewrite.xml
logging/log4j/log4j2/trunk/src/site/xdoc/manual/appenders.xml
logging/log4j/log4j2/trunk/src/site/xdoc/manual/configuration.xml
Modified:
logging/log4j/log4j2/trunk/api/src/main/java/org/apache/logging/log4j/ThreadContext.java
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/api/src/main/java/org/apache/logging/log4j/ThreadContext.java?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/api/src/main/java/org/apache/logging/log4j/ThreadContext.java
(original)
+++
logging/log4j/log4j2/trunk/api/src/main/java/org/apache/logging/log4j/ThreadContext.java
Mon Oct 22 01:15:34 2012
@@ -435,7 +435,7 @@ public final class ThreadContext {
/**
* An immutable ContextStack.
*/
- private static class ImmutableStack extends ThreadContextStack {
+ public static class ImmutableStack extends ThreadContextStack {
private static final long serialVersionUID = 5050502L;
@@ -464,7 +464,7 @@ public final class ThreadContext {
/**
* An immutable Context Map.
*/
- private static class ImmutableMap extends HashMap<String, String> {
+ public static class ImmutableMap extends HashMap<String, String> {
private static final long serialVersionUID = 5050503L;
public ImmutableMap() {
Copied:
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/PropertiesRewritePolicy.java
(from r1400243,
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/MapRewritePolicy.java)
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/PropertiesRewritePolicy.java?p2=logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/PropertiesRewritePolicy.java&p1=logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/MapRewritePolicy.java&r1=1400243&r2=1400744&rev=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/MapRewritePolicy.java
(original)
+++
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/appender/rewrite/PropertiesRewritePolicy.java
Mon Oct 22 01:15:34 2012
@@ -18,36 +18,43 @@ package org.apache.logging.log4j.core.ap
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.LogEvent;
+import org.apache.logging.log4j.core.config.Configuration;
+import org.apache.logging.log4j.core.config.Property;
import org.apache.logging.log4j.core.config.plugins.Plugin;
import org.apache.logging.log4j.core.config.plugins.PluginAttr;
+import org.apache.logging.log4j.core.config.plugins.PluginConfiguration;
import org.apache.logging.log4j.core.config.plugins.PluginElement;
import org.apache.logging.log4j.core.config.plugins.PluginFactory;
import org.apache.logging.log4j.core.helpers.KeyValuePair;
import org.apache.logging.log4j.core.impl.Log4jLogEvent;
-import org.apache.logging.log4j.message.MapMessage;
-import org.apache.logging.log4j.message.Message;
import org.apache.logging.log4j.status.StatusLogger;
+import java.util.Arrays;
import java.util.HashMap;
+import java.util.List;
import java.util.Map;
/**
* This policy modifies events by replacing or possibly adding keys and values
to the MapMessage.
*/
-@Plugin(name = "MapRewritePolicy", type = "Core", elementType =
"rewritePolicy", printObject = true)
-public final class MapRewritePolicy implements RewritePolicy {
+@Plugin(name = "PropertiesRewritePolicy", type = "Core", elementType =
"rewritePolicy", printObject = true)
+public final class PropertiesRewritePolicy implements RewritePolicy {
/**
* Allow subclasses access to the status logger without creating another
instance.
*/
protected static final Logger LOGGER = StatusLogger.getLogger();
- private final Map<String, String> map;
+ private final Map<Property, Boolean> properties;
- private final Mode mode;
+ private final Configuration config;
- private MapRewritePolicy(Map<String, String> map, Mode mode) {
- this.map = map;
- this.mode = mode;
+ private PropertiesRewritePolicy(Configuration config, List<Property>
props) {
+ this.config = config;
+ this.properties = new HashMap<Property, Boolean>(props.size());
+ for (Property prop : props) {
+ boolean interpolate = prop.getValue().contains("${");
+ properties.put(prop, interpolate);
+ }
}
/**
@@ -57,57 +64,31 @@ public final class MapRewritePolicy impl
* @return The LogEvent after rewriting.
*/
public LogEvent rewrite(LogEvent source) {
- Message msg = source.getMessage();
- if (msg == null || !(msg instanceof MapMessage)) {
- return source;
- }
-
- Map<String, String> newMap = new HashMap<String, String>(((MapMessage)
msg).getData());
- switch (mode) {
- case Add: {
- newMap.putAll(map);
- break;
- }
- default: {
- for (Map.Entry<String, String> entry : map.entrySet()) {
- if (newMap.containsKey(entry.getKey())) {
- newMap.put(entry.getKey(), entry.getValue());
- }
- }
+ Map<String, String> props = new HashMap<String,
String>(source.getContextMap());
+ for (Map.Entry<Property, Boolean> entry : properties.entrySet()) {
+ Property prop = entry.getKey();
+ if (!props.containsKey(prop.getName())) {
+ props.put(prop.getName(), entry.getValue() ?
+ config.getSubst().replace(prop.getValue()) :
prop.getValue());
}
}
- MapMessage message = ((MapMessage) msg).newInstance(newMap);
+
return new Log4jLogEvent(source.getLoggerName(), source.getMarker(),
source.getFQCN(), source.getLevel(),
- message, source.getThrown(), source.getContextMap(),
source.getContextStack(), source.getThreadName(),
+ source.getMessage(), source.getThrown(), props,
source.getContextStack(), source.getThreadName(),
source.getSource(), source.getMillis());
}
- /**
- * An enumeration to identify whether keys not in the MapMessage should be
added or whether only existing
- * keys should be updated.
- */
- public enum Mode {
- /**
- * Keys should be added.
- */
- Add,
- /**
- * Keys should be updated.
- */
- Update
- }
-
@Override
public String toString() {
StringBuilder sb = new StringBuilder();
- sb.append("mode=").append(mode);
sb.append(" {");
boolean first = true;
- for (Map.Entry<String, String> entry : map.entrySet()) {
+ for (Map.Entry<Property, Boolean> entry : properties.entrySet()) {
if (!first) {
sb.append(", ");
}
- sb.append(entry.getKey()).append("=").append(entry.getValue());
+ Property prop = entry.getKey();
+ sb.append(prop.getName()).append("=").append(prop.getValue());
first = false;
}
sb.append("}");
@@ -115,46 +96,19 @@ public final class MapRewritePolicy impl
}
/**
- * The factory method to create the MapRewritePolicy.
- * @param mode The string representation of the Mode.
- * @param pairs key/value pairs for the new Map keys and values.
- * @return The MapRewritePolicy.
+ * The factory method to create the PropertiesRewritePolicy.
+ * @param config The Configuration.
+ * @param props key/value pairs for the new keys and values.
+ * @return The PropertiesRewritePolicy.
*/
@PluginFactory
- public static MapRewritePolicy createPolicy(@PluginAttr("mode") String
mode,
- @PluginElement("KeyValuePair")
KeyValuePair[] pairs) {
- Mode op;
- if (mode == null) {
- op = Mode.Add;
- } else {
- op = Mode.valueOf(mode);
- if (op == null) {
- LOGGER.error("Undefined mode " + mode);
- return null;
- }
- }
- if (pairs == null || pairs.length == 0) {
- LOGGER.error("keys and values must be specified for the
MapRewritePolicy");
- return null;
- }
- Map<String, String> map = new HashMap<String, String>();
- for (KeyValuePair pair : pairs) {
- String key = pair.getKey();
- if (key == null) {
- LOGGER.error("A null key is not valid in MapRewritePolicy");
- continue;
- }
- String value = pair.getValue();
- if (value == null) {
- LOGGER.error("A null value for key " + key + " is not allowed
in MapRewritePolicy");
- continue;
- }
- map.put(pair.getKey(), pair.getValue());
- }
- if (map.size() == 0) {
- LOGGER.error("MapRewritePolicy is not configured with any valid
key value pairs");
+ public static PropertiesRewritePolicy createPolicy(@PluginConfiguration
Configuration config,
+ @PluginElement("properties")
Property[] props) {
+ if (props == null || props.length == 0) {
+ LOGGER.error("Properties must be specified for the
PropertiesRewritePolicy");
return null;
}
- return new MapRewritePolicy(map, op);
+ List<Property> properties = Arrays.asList(props);
+ return new PropertiesRewritePolicy(config, properties);
}
}
Modified:
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/config/LoggerConfig.java
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/config/LoggerConfig.java?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/config/LoggerConfig.java
(original)
+++
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/config/LoggerConfig.java
Mon Oct 22 01:15:34 2012
@@ -23,6 +23,7 @@ import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.Filter;
import org.apache.logging.log4j.core.LifeCycle;
+import org.apache.logging.log4j.core.config.plugins.PluginConfiguration;
import org.apache.logging.log4j.core.filter.Filterable;
import org.apache.logging.log4j.core.impl.Log4jLogEvent;
import org.apache.logging.log4j.core.LogEvent;
@@ -63,6 +64,8 @@ public class LoggerConfig extends Filter
private LoggerConfig parent;
private AtomicInteger counter = new AtomicInteger();
private boolean shutdown = false;
+ private final Map<Property, Boolean> properties;
+ private final Configuration config;
/**
@@ -72,6 +75,8 @@ public class LoggerConfig extends Filter
this.logEventFactory = this;
this.level = Level.ERROR;
this.name = "";
+ this.properties = null;
+ this.config = null;
}
/**
@@ -85,16 +90,28 @@ public class LoggerConfig extends Filter
this.name = name;
this.level = level;
this.additive = additive;
+ this.properties = null;
+ this.config = null;
}
protected LoggerConfig(String name, List<AppenderRef> appenders, Filter
filter, Level level,
- boolean additive) {
+ boolean additive, Property[] properties,
Configuration config) {
super(filter);
this.logEventFactory = this;
this.name = name;
this.appenderRefs = appenders;
this.level = level;
this.additive = additive;
+ this.config = config;
+ if (properties != null && properties.length > 0) {
+ this.properties = new HashMap<Property,
Boolean>(properties.length);
+ for (Property prop : properties) {
+ boolean interpolate = prop.getValue().contains("${");
+ this.properties.put(prop, interpolate);
+ }
+ } else {
+ this.properties = null;
+ }
}
@Override
@@ -249,7 +266,17 @@ public class LoggerConfig extends Filter
* @param t A Throwable or null.
*/
public void log(String loggerName, Marker marker, String fqcn, Level
level, Message data, Throwable t) {
- LogEvent event = logEventFactory.createEvent(loggerName, marker, fqcn,
level, data, t);
+ List<Property> props = null;
+ if (properties != null) {
+ props = new ArrayList<Property>(properties.size());
+
+ for (Map.Entry<Property, Boolean> entry : properties.entrySet()) {
+ Property prop = entry.getKey();
+ String value = entry.getValue() ?
config.getSubst().replace(prop.getValue()) : prop.getValue();
+ props.add(Property.createProperty(prop.getName(), value));
+ }
+ }
+ LogEvent event = logEventFactory.createEvent(loggerName, marker, fqcn,
level, data, props, t);
log(event);
}
@@ -319,8 +346,8 @@ public class LoggerConfig extends Filter
* @return The LogEvent.
*/
public LogEvent createEvent(String loggerName, Marker marker, String fqcn,
Level level, Message data,
- Throwable t) {
- return new Log4jLogEvent(loggerName, marker, fqcn, level, data, t);
+ List<Property> properties, Throwable t) {
+ return new Log4jLogEvent(loggerName, marker, fqcn, level, data,
properties, t);
}
@Override
@@ -342,6 +369,8 @@ public class LoggerConfig extends Filter
@PluginAttr("level") String
loggerLevel,
@PluginAttr("name") String
loggerName,
@PluginElement("appender-ref")
AppenderRef[] refs,
+ @PluginElement("properties")
Property[] properties,
+ @PluginConfiguration Configuration
config,
@PluginElement("filters") Filter
filter) {
if (loggerName == null) {
LOGGER.error("Loggers cannot be configured without a name");
@@ -359,7 +388,7 @@ public class LoggerConfig extends Filter
String name = loggerName.equals("root") ? "" : loggerName;
boolean additive = additivity == null ? true :
Boolean.parseBoolean(additivity);
- return new LoggerConfig(name, appenderRefs, filter, level, additive);
+ return new LoggerConfig(name, appenderRefs, filter, level, additive,
properties, config);
}
/**
@@ -372,6 +401,8 @@ public class LoggerConfig extends Filter
public static LoggerConfig createLogger(@PluginAttr("additivity")
String additivity,
@PluginAttr("level") String
loggerLevel,
@PluginElement("appender-ref")
AppenderRef[] refs,
+ @PluginElement("properties")
Property[] properties,
+ @PluginConfiguration Configuration
config,
@PluginElement("filters") Filter
filter) {
List<AppenderRef> appenderRefs = Arrays.asList(refs);
Level level;
@@ -383,7 +414,8 @@ public class LoggerConfig extends Filter
}
boolean additive = additivity == null ? true :
Boolean.parseBoolean(additivity);
- return new LoggerConfig(LogManager.ROOT_LOGGER_NAME, appenderRefs,
filter, level, additive);
+ return new LoggerConfig(LogManager.ROOT_LOGGER_NAME, appenderRefs,
filter, level, additive, properties,
+ config);
}
}
Modified:
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/Log4jLogEvent.java
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/Log4jLogEvent.java?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/Log4jLogEvent.java
(original)
+++
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/Log4jLogEvent.java
Mon Oct 22 01:15:34 2012
@@ -20,6 +20,7 @@ import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.ThreadContext;
import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.core.LogEvent;
+import org.apache.logging.log4j.core.config.Property;
import org.apache.logging.log4j.message.LoggerNameAwareMessage;
import org.apache.logging.log4j.message.Message;
import org.apache.logging.log4j.message.TimestampMessage;
@@ -27,6 +28,8 @@ import org.apache.logging.log4j.message.
import java.io.InvalidObjectException;
import java.io.ObjectInputStream;
import java.io.Serializable;
+import java.util.HashMap;
+import java.util.List;
import java.util.Map;
/**
@@ -58,8 +61,22 @@ public class Log4jLogEvent implements Lo
* @param t A Throwable or null.
*/
public Log4jLogEvent(String loggerName, Marker marker, String fqcn, Level
level, Message message, Throwable t) {
+ this(loggerName, marker, fqcn, level, message, null, t);
+ }
+
+ /**
+ * Constructor.
+ * @param loggerName The name of the Logger.
+ * @param marker The Marker or null.
+ * @param fqcn The fully qualified class name of the caller.
+ * @param level The logging Level.
+ * @param message The Message.
+ * @param t A Throwable or null.
+ */
+ public Log4jLogEvent(String loggerName, Marker marker, String fqcn, Level
level, Message message,
+ List<Property> properties, Throwable t) {
this(loggerName, marker, fqcn, level, message, t,
- ThreadContext.getContext().size() == 0 ? null :
ThreadContext.getImmutableContext(),
+ createMap(properties),
ThreadContext.getDepth() == 0 ? null : ThreadContext.cloneStack(),
null,
null, System.currentTimeMillis());
}
@@ -97,6 +114,23 @@ public class Log4jLogEvent implements Lo
}
}
+ private static Map<String, String> createMap(List<Property> properties) {
+ if (ThreadContext.isEmpty() && (properties == null ||
properties.size() == 0)) {
+ return null;
+ }
+ if (properties == null || properties.size() == 0) {
+ return ThreadContext.getImmutableContext();
+ }
+ Map<String, String> map = ThreadContext.getContext();
+
+ for (Property prop : properties) {
+ if (!map.containsKey(prop.getName())) {
+ map.put(prop.getName(), prop.getValue());
+ }
+ }
+ return new ThreadContext.ImmutableMap(map);
+ }
+
/**
* Returns the logging Level.
* @return the Level associated with this event.
Modified:
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/LogEventFactory.java
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/LogEventFactory.java?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/LogEventFactory.java
(original)
+++
logging/log4j/log4j2/trunk/core/src/main/java/org/apache/logging/log4j/core/impl/LogEventFactory.java
Mon Oct 22 01:15:34 2012
@@ -20,12 +20,16 @@ package org.apache.logging.log4j.core.im
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.Marker;
import org.apache.logging.log4j.core.LogEvent;
+import org.apache.logging.log4j.core.config.Property;
import org.apache.logging.log4j.message.Message;
+import java.util.List;
+
/**
*
*/
public interface LogEventFactory {
- LogEvent createEvent(String loggerName, Marker marker, String fqcn, Level
level, Message data, Throwable t);
+ LogEvent createEvent(String loggerName, Marker marker, String fqcn, Level
level, Message data,
+ List<Property> properties, Throwable t);
}
Modified:
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/appender/rewrite/RewriteAppenderTest.java
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/appender/rewrite/RewriteAppenderTest.java?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/appender/rewrite/RewriteAppenderTest.java
(original)
+++
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/appender/rewrite/RewriteAppenderTest.java
Mon Oct 22 01:15:34 2012
@@ -18,6 +18,7 @@ package org.apache.logging.log4j.core.ap
import org.apache.logging.log4j.EventLogger;
import org.apache.logging.log4j.LogManager;
+import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.LogEvent;
import org.apache.logging.log4j.core.LoggerContext;
@@ -37,6 +38,7 @@ import java.util.Map;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertTrue;
+import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertEquals;
/**
@@ -46,6 +48,7 @@ public class RewriteAppenderTest {
private static final String CONFIG = "log4j-rewrite.xml";
private static Configuration config;
private static ListAppender app;
+ private static ListAppender app2;
private static LoggerContext ctx;
@BeforeClass
@@ -56,7 +59,8 @@ public class RewriteAppenderTest {
for (Map.Entry<String, Appender> entry :
config.getAppenders().entrySet()) {
if (entry.getKey().equals("List")) {
app = (ListAppender) entry.getValue();
- break;
+ } else if (entry.getKey().equals("List2")) {
+ app2 = (ListAppender) entry.getValue();
}
}
}
@@ -86,5 +90,17 @@ public class RewriteAppenderTest {
assertTrue("Incorrect number of map entries, expected 3 got " +
map.size(), map.size() == 3);
String value = map.get("Key1");
assertEquals("Apache", value);
+ app.clear();
+ }
+
+
+ @Test
+ public void testProperties() {
+ Logger logger = LogManager.getLogger(RewriteAppenderTest.class);
+ logger.debug("Test properties rewrite");
+ List<String> list = app2.getMessages();
+ assertNotNull("No events generated", list);
+ assertTrue("Incorrect number of events. Expected 1, got " +
list.size(), list.size() == 1);
+ assertFalse("Did not resolve user name",
list.get(0).contains("{user.dir}"));
}
}
Copied:
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLLoggerPropsTest.java
(from r1397892,
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLConfigurationPropsTest.java)
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLLoggerPropsTest.java?p2=logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLLoggerPropsTest.java&p1=logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLConfigurationPropsTest.java&r1=1397892&r2=1400744&rev=1400744&view=diff
==============================================================================
---
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLConfigurationPropsTest.java
(original)
+++
logging/log4j/log4j2/trunk/core/src/test/java/org/apache/logging/log4j/core/config/XMLLoggerPropsTest.java
Mon Oct 22 01:15:34 2012
@@ -17,71 +17,68 @@
package org.apache.logging.log4j.core.config;
import org.apache.logging.log4j.LogManager;
+import org.apache.logging.log4j.Logger;
+import org.apache.logging.log4j.core.Appender;
import org.apache.logging.log4j.core.LoggerContext;
import org.apache.logging.log4j.status.StatusLogger;
+import org.apache.logging.log4j.test.appender.ListAppender;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
-import static org.junit.Assert.*;
+import java.util.List;
+import java.util.Map;
+
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
/**
*
*/
-public class XMLConfigurationPropsTest {
+public class XMLLoggerPropsTest {
- private static final String CONFIG = "log4j-props.xml";
- private static final String LOGFILE = "target/test.log";
+ private static final String CONFIG = "log4j-loggerprops.xml";
+ private static Configuration config;
+ private static ListAppender app;
+ private static LoggerContext ctx;
@BeforeClass
public static void setupClass() {
+
System.setProperty(XMLConfigurationFactory.CONFIGURATION_FILE_PROPERTY, CONFIG);
+ System.setProperty("test", "test");
+ ctx = (LoggerContext) LogManager.getContext(false);
+ config = ctx.getConfiguration();
+ for (Map.Entry<String, Appender> entry :
config.getAppenders().entrySet()) {
+ if (entry.getKey().equals("List")) {
+ app = (ListAppender) entry.getValue();
+ break;
+ }
+ }
}
@AfterClass
public static void cleanupClass() {
System.clearProperty(XMLConfigurationFactory.CONFIGURATION_FILE_PROPERTY);
- LoggerContext ctx = (LoggerContext) LogManager.getContext();
ctx.reconfigure();
StatusLogger.getLogger().reset();
}
@Test
- public void testNoProps() {
-
System.setProperty(XMLConfigurationFactory.CONFIGURATION_FILE_PROPERTY, CONFIG);
- LoggerContext ctx = (LoggerContext) LogManager.getContext();
- ctx.reconfigure();
- Configuration config = ctx.getConfiguration();
- assertTrue("Configuration is not an XMLConfiguration", config
instanceof XMLConfiguration);
- }
-
- @Test
- public void testWithConfigProp() {
-
System.setProperty(XMLConfigurationFactory.CONFIGURATION_FILE_PROPERTY, CONFIG);
- System.setProperty("log4j.level", "debug");
- try {
- LoggerContext ctx = (LoggerContext) LogManager.getContext();
- ctx.reconfigure();
- Configuration config = ctx.getConfiguration();
- assertTrue("Configuration is not an XMLConfiguration", config
instanceof XMLConfiguration);
- } finally {
- System.clearProperty("log4j.level");
-
- }
- }
-
- @Test
public void testWithProps() {
-
System.setProperty(XMLConfigurationFactory.CONFIGURATION_FILE_PROPERTY, CONFIG);
- System.setProperty("log4j.level", "debug");
- System.setProperty("log.level", "debug");
+ assertNotNull("No List Appender", app);
+
try {
- LoggerContext ctx = (LoggerContext) LogManager.getContext();
- ctx.reconfigure();
- Configuration config = ctx.getConfiguration();
assertTrue("Configuration is not an XMLConfiguration", config
instanceof XMLConfiguration);
+ Logger logger = LogManager.getLogger(XMLLoggerPropsTest.class);
+ logger.debug("Test with props");
+ logger = LogManager.getLogger("tiny.bubbles");
+ logger.debug("Test on root");
+ List<String> events = app.getMessages();
+ assertTrue("No events", events.size() > 0);
+ assertTrue("Incorrect number of events", events.size() == 2);
+ assertTrue("Incorrect value", events.get(0).contains("test=test"));
} finally {
- System.clearProperty("log4j.level");
- System.clearProperty("log.level");
+ System.clearProperty("test");
}
}
}
Copied:
logging/log4j/log4j2/trunk/core/src/test/resources/log4j-loggerprops.xml (from
r1397892, logging/log4j/log4j2/trunk/core/src/test/resources/log4j-props.xml)
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/test/resources/log4j-loggerprops.xml?p2=logging/log4j/log4j2/trunk/core/src/test/resources/log4j-loggerprops.xml&p1=logging/log4j/log4j2/trunk/core/src/test/resources/log4j-props.xml&r1=1397892&r2=1400744&rev=1400744&view=diff
==============================================================================
--- logging/log4j/log4j2/trunk/core/src/test/resources/log4j-props.xml
(original)
+++ logging/log4j/log4j2/trunk/core/src/test/resources/log4j-loggerprops.xml
Mon Oct 22 01:15:34 2012
@@ -1,14 +1,21 @@
<?xml version="1.0" encoding="UTF-8"?>
-<configuration status="${sys:log4j.level}" strict="false" name="DSI"
packages="com.terradue.dsione">
+<configuration status="error" strict="false" name="DSI"
packages="org.apache.logging.log4j.test">
<appenders>
- <Console name="Console" target="SYSTEM_OUT">
- <PatternLayout pattern="[%-5level] %msg%n" />
- </Console>
+ <List name="List">
+ <PatternLayout pattern="[%-5level] %c{1.} user=%X{user} test=%X{test}
%msg%n" />
+ </List>
</appenders>
<loggers>
- <root level="${sys:log.level}">
- <appender-ref ref="Console" />
+ <logger name="org.apache.logging.log4j.core" level="debug"
additivity="false">
+ <property name="user">$${sys:user.name}</property>
+ <property name="test">${sys:test}</property>
+ <appender-ref ref="List"/>
+ </logger>
+ <root level="debug">
+ <property name="user">${sys:user.name}</property>
+ <property name="test">${sys:test}</property>
+ <appender-ref ref="List" />
</root>
</loggers>
</configuration>
\ No newline at end of file
Modified: logging/log4j/log4j2/trunk/core/src/test/resources/log4j-rewrite.xml
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/core/src/test/resources/log4j-rewrite.xml?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
--- logging/log4j/log4j2/trunk/core/src/test/resources/log4j-rewrite.xml
(original)
+++ logging/log4j/log4j2/trunk/core/src/test/resources/log4j-rewrite.xml Mon
Oct 22 01:15:34 2012
@@ -20,18 +20,27 @@
<appenders>
<Console name="STDOUT">
- <PatternLayout pattern="%m%n"/>
+ <PatternLayout pattern="%X %m%n"/>
</Console>
<List name="List">
<ThresholdFilter level="debug"/>
</List>
+ <List name="List2">
+ <PatternLayout pattern="[%-5level] %c{1.} user=%X{user} os=%X{os}
%msg%n" />
+ </List>
<Rewrite name="Rewrite">
<MapRewritePolicy>
<KeyValuePair key="Key1" Value="Apache"/>
<KeyValuePair key="Key3" Value="Log4j"/>
</MapRewritePolicy>
<appender-ref ref="List"/>
-
+ </Rewrite>
+ <Rewrite name="Rewrite2">
+ <PropertiesRewritePolicy>
+ <Property name="user">$${sys:user.name}</Property>
+ <Property name="os">${sys:os.name}</Property>
+ </PropertiesRewritePolicy>
+ <appender-ref ref="List2"/>
</Rewrite>
</appenders>
@@ -40,6 +49,9 @@
<appender-ref ref="Rewrite"/>
</logger>
+ <logger name="org.apache.logging.log4j" level="trace" additivity="false">
+ <appender-ref ref="Rewrite2"/>
+ </logger>
<root level="error">
<appender-ref ref="STDOUT"/>
</root>
Modified: logging/log4j/log4j2/trunk/src/site/xdoc/manual/appenders.xml
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/src/site/xdoc/manual/appenders.xml?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
--- logging/log4j/log4j2/trunk/src/site/xdoc/manual/appenders.xml (original)
+++ logging/log4j/log4j2/trunk/src/site/xdoc/manual/appenders.xml Mon Oct 22
01:15:34 2012
@@ -912,6 +912,51 @@
</configuration>
]]></source>
</p>
+ <h5>PropertiesRewritePolicy</h5>
+ <p>
+ PropertiesRewritePolicy will add properties configured on the
policy to the ThreadContext Map
+ being logged. The properties will not be added to the actual
ThreadContext Map. The property
+ values may contain variables that will be evaluated when the
configuration is processed as
+ well as when the event is logged.
+ </p>
+ <table border="1" width="100%">
+ <tr>
+ <th>Parameter Name</th>
+ <th>Type</th>
+ <th>Description</th>
+ </tr>
+ <tr>
+ <td>properties</td>
+ <td>Property[]</td>
+ <td>One of more Property elements to define the keys and values
to be added to the ThreadContext Map.</td>
+ </tr>
+ </table>
+ <p>
+ The following configuration shows a RewriteAppender configured to
add a product key and its value
+ to the MapMessage.:
+
+ <source><![CDATA[<?xml version="1.0" encoding="UTF-8"?>
+<configuration status="warn" name="MyApp" packages="">
+ <appenders>
+ <Console name="STDOUT" target="SYSTEM_OUT">
+ <PatternLayout pattern="%m%n"/>
+ </Console>
+ <Rewrite name="rewrite">
+ <appender-ref ref="STDOUT"/>
+ <PropertiesRewritePolicy>
+ <Property key="user">${sys:user.name}</Property>
+ <Property key="env">${sys:environment}</Property>
+ </PropertiesRewritePolicy>
+ </Rewrite>
+ </appenders>
+ <loggers>
+ <root level="error">
+ <appender-ref ref="Rewrite"/>
+ </root>
+ </loggers>
+</configuration>
+ ]]></source>
+ </p>
</subsection>
<a name="RollingFileAppender"/>
<subsection name="RollingFileAppender">
Modified: logging/log4j/log4j2/trunk/src/site/xdoc/manual/configuration.xml
URL:
http://svn.apache.org/viewvc/logging/log4j/log4j2/trunk/src/site/xdoc/manual/configuration.xml?rev=1400744&r1=1400743&r2=1400744&view=diff
==============================================================================
--- logging/log4j/log4j2/trunk/src/site/xdoc/manual/configuration.xml (original)
+++ logging/log4j/log4j2/trunk/src/site/xdoc/manual/configuration.xml Mon Oct
22 01:15:34 2012
@@ -566,6 +566,14 @@
the default value of false will be used.
</p>
<p>
+ A LoggerConfig (including the root LoggerConfig) can be configured
with properties that will be added
+ to the properties copied from the ThreadContextMap. These
properties can be referenced from Appenders,
+ Filters, Layouts, etc just as if they were part of the
ThreadContext Map. The properties can contain
+ variables that will be resolved either when the configuration is
parsed or dynamically when each
+ event is logged. See <a href="#PropertySubstitution">Property
Substitution</a> for more information on
+ using variables.
+ </p>
+ <p>
The LoggerConfig may also be configured with one or more
appender-ref elements. Each appender
referenced will become associated with the specified LoggerConfig.
If multiple appenders
are configured on the LoggerConfig each of them be called when
processing logging events.
@@ -648,6 +656,7 @@
</logger>>
<logger name="org.apache.logging.log4j.test2" level="debug"
additivity="false">
+ <property name="user">${sys:user.name}</property>
<appender-ref ref="File">
<ThreadContextMapFilter>
<KeyValuePair key="test" value="123"/>