You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@mina.apache.org by ma...@apache.org on 2007/10/23 23:29:17 UTC
svn commit: r587660 - in /mina/trunk:
core/src/main/java/org/apache/mina/filter/logging/
core/src/test/java/org/apache/mina/filter/logging/
example/src/main/resources/
example/src/main/resources/org/apache/mina/example/chat/
Author: maarten
Date: Tue Oct 23 14:29:16 2007
New Revision: 587660
URL: http://svn.apache.org/viewvc?rev=587660&view=rev
Log:
MdcInjectionFilter: added constructor that takes EnumSet of all keys to should be set in the MDC
Modified:
mina/trunk/core/src/main/java/org/apache/mina/filter/logging/MdcInjectionFilter.java
mina/trunk/core/src/test/java/org/apache/mina/filter/logging/MdcInjectionFilterTest.java
mina/trunk/example/src/main/resources/log4j.properties
mina/trunk/example/src/main/resources/org/apache/mina/example/chat/serverContext.xml
Modified: mina/trunk/core/src/main/java/org/apache/mina/filter/logging/MdcInjectionFilter.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/main/java/org/apache/mina/filter/logging/MdcInjectionFilter.java?rev=587660&r1=587659&r2=587660&view=diff
==============================================================================
--- mina/trunk/core/src/main/java/org/apache/mina/filter/logging/MdcInjectionFilter.java (original)
+++ mina/trunk/core/src/main/java/org/apache/mina/filter/logging/MdcInjectionFilter.java Tue Oct 23 14:29:16 2007
@@ -22,6 +22,9 @@
import java.net.InetSocketAddress;
import java.util.HashMap;
import java.util.Map;
+import java.util.Set;
+import java.util.HashSet;
+import java.util.EnumSet;
import org.apache.mina.common.AttributeKey;
import org.apache.mina.common.IoFilterEvent;
@@ -35,7 +38,7 @@
* These properties will be set in the MDC for all logging events that are generated
* down the call stack, even in code that is not aware of MINA.
*
- * The following properties will be set for all transports:
+ * By default, the following properties will be set for all transports:
* <ul>
* <li>"handlerClass"</li>
* <li>"remoteAddress"</li>
@@ -66,9 +69,16 @@
public class MdcInjectionFilter extends WrappingFilter {
+ public enum MdcKey {
+ handlerClass, remoteAddress, localAddress,
+ remoteIp, remotePort, localIp, localPort }
+
/** key used for storing the context map in the IoSession */
private static final AttributeKey CONTEXT_KEY = new AttributeKey(MdcInjectionFilter.class, "context");
+ /** key used for storing the mDCInjectionFilter itself in the IoSession */
+ private static final AttributeKey MDC_FILTER_KEY = new AttributeKey(MdcInjectionFilter.class, "mdcFilter");
+
private ThreadLocal<Integer> callDepth = new ThreadLocal<Integer>() {
@Override
protected Integer initialValue() {
@@ -76,12 +86,50 @@
}
};
+ private EnumSet<MdcKey> mdcKeys;
+
+ /**
+ * Use this constructor when you want to specify which keys to add to the MDC.
+ * You could still add custom keys via <code>setproperty</code>
+ * @param keys set of keys that should be added to the MDC
+ *
+ * @see #setProperty(org.apache.mina.common.IoSession, String, String)
+ */
+ public MdcInjectionFilter(EnumSet<MdcKey> keys) {
+ this.mdcKeys = keys;
+ }
+
+ /**
+ * Use this constructor when you want to specify which keys to add to the MDC
+ * You could still add custom keys via <code>setProperty</code>
+ * @param keys list of keys that should be added to the MDC
+ *
+ * @see #setProperty(org.apache.mina.common.IoSession, String, String)
+ */
+ public MdcInjectionFilter(MdcKey... keys) {
+ Set<MdcKey> keySet = new HashSet<MdcKey>();
+ for (MdcKey key : keys) {
+ keySet.add(key);
+ }
+ this.mdcKeys = EnumSet.copyOf(keySet);
+ }
+
+
+ public MdcInjectionFilter() {
+ this.mdcKeys = EnumSet.allOf(MdcKey.class);
+ }
+
@Override
protected void filter(IoFilterEvent event) throws Exception {
// since this method can potentially call into itself
// we need to check the call depth before clearing the MDC
callDepth.set (callDepth.get() + 1);
- Context context = getContext(event.getSession());
+ Context context = getAndFillContext(event.getSession());
+
+ if (event.getSession().getAttribute(MDC_FILTER_KEY) == null) {
+ event.getSession().setAttribute(MDC_FILTER_KEY, this);
+ }
+
/* copy context to the MDC */
for (Map.Entry<String,String> e : context.entrySet()) {
MDC.put(e.getKey(), e.getValue());
@@ -101,12 +149,18 @@
}
}
+ private Context getAndFillContext(final IoSession session) {
+ Context context = getContext(session);
+ if (context.isEmpty()) {
+ fillContext(session, context);
+ }
+ return context;
+ }
private static Context getContext(final IoSession session) {
Context context = (Context) session.getAttribute(CONTEXT_KEY);
if (context == null) {
context = new Context();
- fillContext(session, context);
session.setAttribute(CONTEXT_KEY, context);
}
return context;
@@ -118,17 +172,31 @@
* @param session the session to map
* @param context key properties will be added to this map
*/
- protected static void fillContext(final IoSession session, final Context context) {
- context.put("handlerClass", session.getHandler().getClass().getName());
- context.put("remoteAddress", session.getRemoteAddress().toString());
- context.put("localAddress", session.getLocalAddress().toString());
+ protected void fillContext(final IoSession session, final Context context) {
+ if (mdcKeys.contains(MdcKey.handlerClass)) {
+ context.put(MdcKey.handlerClass.name(), session.getHandler().getClass().getName());
+ }
+ if (mdcKeys.contains(MdcKey.remoteAddress)) {
+ context.put(MdcKey.remoteAddress.name(), session.getRemoteAddress().toString());
+ }
+ if (mdcKeys.contains(MdcKey.localAddress)) {
+ context.put(MdcKey.localAddress.name(), session.getLocalAddress().toString());
+ }
if (session.getTransportMetadata().getAddressType() == InetSocketAddress.class) {
InetSocketAddress remoteAddress = (InetSocketAddress) session.getRemoteAddress();
InetSocketAddress localAddress = (InetSocketAddress) session.getLocalAddress();
- context.put("remoteIp", remoteAddress.getAddress().getHostAddress());
- context.put("remotePort", String.valueOf(remoteAddress.getPort()));
- context.put("localIp", localAddress.getAddress().getHostAddress());
- context.put("localPort", String.valueOf(localAddress.getPort()));
+ if (mdcKeys.contains(MdcKey.remoteIp)) {
+ context.put(MdcKey.remoteIp.name(), remoteAddress.getAddress().getHostAddress());
+ }
+ if (mdcKeys.contains(MdcKey.remotePort)) {
+ context.put(MdcKey.remotePort.name(), String.valueOf(remoteAddress.getPort()));
+ }
+ if (mdcKeys.contains(MdcKey.localIp)) {
+ context.put(MdcKey.localIp.name(), localAddress.getAddress().getHostAddress());
+ }
+ if (mdcKeys.contains(MdcKey.localPort)) {
+ context.put(MdcKey.localPort.name(), String.valueOf(localAddress.getPort()));
+ }
}
}
@@ -162,6 +230,11 @@
private static class Context extends HashMap<String,String> {
private static final long serialVersionUID = -673025693009555560L;
+ }
+
+ public static void main(String[] args) {
+ String s = MdcKey.handlerClass.name();
+ System.out.println("s = " + s);
}
}
Modified: mina/trunk/core/src/test/java/org/apache/mina/filter/logging/MdcInjectionFilterTest.java
URL: http://svn.apache.org/viewvc/mina/trunk/core/src/test/java/org/apache/mina/filter/logging/MdcInjectionFilterTest.java?rev=587660&r1=587659&r2=587660&view=diff
==============================================================================
--- mina/trunk/core/src/test/java/org/apache/mina/filter/logging/MdcInjectionFilterTest.java (original)
+++ mina/trunk/core/src/test/java/org/apache/mina/filter/logging/MdcInjectionFilterTest.java Tue Oct 23 14:29:16 2007
@@ -32,13 +32,7 @@
import org.apache.log4j.AppenderSkeleton;
import org.apache.log4j.Level;
import org.apache.log4j.spi.LoggingEvent;
-import org.apache.mina.common.IoBuffer;
-import org.apache.mina.common.ConnectFuture;
-import org.apache.mina.common.DefaultIoFilterChainBuilder;
-import org.apache.mina.common.IdleStatus;
-import org.apache.mina.common.IoFilterAdapter;
-import org.apache.mina.common.IoHandlerAdapter;
-import org.apache.mina.common.IoSession;
+import org.apache.mina.common.*;
import org.apache.mina.filter.codec.ProtocolCodecFactory;
import org.apache.mina.filter.codec.ProtocolCodecFilter;
import org.apache.mina.filter.codec.ProtocolDecoder;
@@ -148,6 +142,44 @@
chain.addLast("executor2" , new ExecutorFilter());
chain.addLast("mdc-injector2", mdcInjectionFilter);
test(chain);
+ }
+
+ public void testOnlyRemoteAddress() throws IOException, InterruptedException {
+ DefaultIoFilterChainBuilder chain = new DefaultIoFilterChainBuilder();
+ chain.addFirst("mdc-injector", new MdcInjectionFilter(
+ MdcInjectionFilter.MdcKey.remoteAddress));
+ chain.addLast("dummy", new DummyIoFilter());
+ chain.addLast("protocol", new ProtocolCodecFilter(new DummyProtocolCodecFactory()));
+ SimpleIoHandler simpleIoHandler = new SimpleIoHandler();
+ acceptor.setHandler(simpleIoHandler);
+ acceptor.setLocalAddress(new InetSocketAddress(PORT));
+ acceptor.bind();
+ acceptor.setFilterChainBuilder(chain);
+ // create some clients
+ NioSocketConnector connector = new NioSocketConnector();
+ connector.setHandler(new IoHandlerAdapter());
+ SocketAddress remoteAddressClients[] = new SocketAddress[2];
+ remoteAddressClients[0] = connectAndWrite(connector,0);
+ remoteAddressClients[1] = connectAndWrite(connector,1);
+ // wait until Iohandler has received all events
+ simpleIoHandler.messageSentLatch.await();
+ simpleIoHandler.sessionIdleLatch.await();
+ simpleIoHandler.sessionClosedLatch.await();
+ // make a copy to prevent ConcurrentModificationException
+ List<LoggingEvent> events = new ArrayList<LoggingEvent>(appender.events);
+ // verify that all logging events have correct MDC
+ for (LoggingEvent event : events) {
+ for (MdcInjectionFilter.MdcKey mdcKey : MdcInjectionFilter.MdcKey.values()) {
+ String key = mdcKey.name();
+ Object value = event.getMDC(key);
+ if (mdcKey == MdcInjectionFilter.MdcKey.remoteAddress) {
+ assertNotNull(
+ "MDC[remoteAddress] not set for [" + event.getMessage() + "]", value);
+ } else {
+ assertNull("MDC[" + key + "] set for [" + event.getMessage() + "]", value);
+ }
+ }
+ }
}
private void test(DefaultIoFilterChainBuilder chain) throws IOException, InterruptedException {
Modified: mina/trunk/example/src/main/resources/log4j.properties
URL: http://svn.apache.org/viewvc/mina/trunk/example/src/main/resources/log4j.properties?rev=587660&r1=587659&r2=587660&view=diff
==============================================================================
--- mina/trunk/example/src/main/resources/log4j.properties (original)
+++ mina/trunk/example/src/main/resources/log4j.properties Tue Oct 23 14:29:16 2007
@@ -7,4 +7,4 @@
log4j.appender.stdout.layout.ConversionPattern=[%d{HH:mm:ss}] %p [%c] - %m%n
# you could use this pattern to test the MDC with the Chat server
-#log4j.appender.stdout.layout.ConversionPattern=[%d{HH:mm:ss}] %t %p %X{name} [%X{user}] [%X{remoteIp}:%X{remotePort}] [%c] - %m%n
\ No newline at end of file
+# log4j.appender.stdout.layout.ConversionPattern=[%d{HH:mm:ss}] %t %p %X{name} [%X{user}] [%X{remoteAddress}] [%c] - %m%n
\ No newline at end of file
Modified: mina/trunk/example/src/main/resources/org/apache/mina/example/chat/serverContext.xml
URL: http://svn.apache.org/viewvc/mina/trunk/example/src/main/resources/org/apache/mina/example/chat/serverContext.xml?rev=587660&r1=587659&r2=587660&view=diff
==============================================================================
--- mina/trunk/example/src/main/resources/org/apache/mina/example/chat/serverContext.xml (original)
+++ mina/trunk/example/src/main/resources/org/apache/mina/example/chat/serverContext.xml Tue Oct 23 14:29:16 2007
@@ -40,7 +40,9 @@
<property name="filters">
<list>
<bean class="org.apache.mina.filter.executor.ExecutorFilter"/>
- <bean class="org.apache.mina.filter.logging.MdcInjectionFilter"/>
+ <bean class="org.apache.mina.filter.logging.MdcInjectionFilter">
+ <constructor-arg value="remoteAddress"/>
+ </bean>
<bean class="org.apache.mina.filter.codec.ProtocolCodecFilter">
<constructor-arg>
<bean class="org.apache.mina.filter.codec.textline.TextLineCodecFactory" />