Log4j MDC (Mapped Diagnostic Context) : Example code

by Veera on November 2, 2009

in Java

As a continuation of my previous post about Log4j MDC (Mapped Diagnostic Context), here’s a fully working code sample explaining the concept. This is a simple example where we have a one servlet and one filter. The filter intercepts each and every request and put the user name in the MDC.

The Simple Servlet Class

package com.veerasundar.code.log4jmdc;

import java.io.IOException;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.log4j.Logger;

/**
 * A good-for-nothing servlet which is just writing few messages to the logger
 * object. Since we've configured in the log4j.properties file to include the
 * userName, taken from MDC, every message will be appended with the user name
 * that is set from the AuthenticationFilter
 *
 * @author veerasundar.com/blog
 */
public class Log4jMdcDemo extends HttpServlet {

	private static Logger logger = Logger.getLogger(Log4jMdcDemo.class);

	private static final long serialVersionUID = 1L;

	public Log4jMdcDemo() {
	}

	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse
	 *      response)
	 */
	protected void doGet(HttpServletRequest request,
			HttpServletResponse response) throws ServletException, IOException {
		doService(request, response);
	}

	/**
	 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse
	 *      response)
	 */
	protected void doPost(HttpServletRequest request,
			HttpServletResponse response) throws ServletException, IOException {
		doService(request, response);
	}

	protected void doService(HttpServletRequest request,
			HttpServletResponse response) throws ServletException, IOException {

		logger.info("This is  demo for the Log4j MDC concept");
		logger.info("From Veerasundar.com/blog");
		logger.debug("Just some sample messages");
	}
}

A Filter to put the user name in MDC for every request call

package com.veerasundar.code.log4jmdc;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;

import org.apache.log4j.MDC;

/**
 * An example authentication filter which is used to intercept all the requests
 * for fetching the user name from it and put the user name to the Log4j Mapped
 * Diagnostic Context (MDC), so that the user name could be used for
 * differentiating log messages.
 *
 * @author veerasundar.com/blog
 *
 */
public class AuthenticationFilter implements Filter {

	@Override
	public void doFilter(ServletRequest request, ServletResponse response,
			FilterChain chain) throws IOException, ServletException {

		try {
			/*
			 * This code puts the value "userName" to the Mapped Diagnostic
			 * context. Since MDc is a static class, we can directly access it
			 * with out creating a new object from it. Here, instead of hard
			 * coding the user name, the value can be retrieved from a HTTP
			 * Request object.
			 */
			MDC.put("userName", "veera");

			chain.doFilter(request, response);

		} finally {
			MDC.remove("userName");
		}

	}

	@Override
	public void init(FilterConfig arg0) throws ServletException {
	}

	@Override
	public void destroy() {
	}

}

Web.xml file to glue together Servlet and Filter

<?xml version="1.0" encoding="UTF-8"?>
<web-app id="WebApp_ID" version="2.4"
	xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
	xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
	<servlet>
		<description>
		</description>
		<display-name>Log4jMdcDemo</display-name>
		<servlet-name>Log4jMdcDemo</servlet-name>
		<servlet-class>com.veerasundar.code.log4jmdc.Log4jMdcDemo</servlet-class>
	</servlet>
	<servlet-mapping>
		<servlet-name>Log4jMdcDemo</servlet-name>
		<url-pattern>/Log4jMdcDemo</url-pattern>
	</servlet-mapping>

	<filter>
		<filter-name>AuthFilter</filter-name>
		<filter-class>com.veerasundar.code.log4jmdc.AuthenticationFilter</filter-class>
	</filter>

	<filter-mapping>
		<filter-name>AuthFilter</filter-name>
		<url-pattern>/*</url-pattern>
	</filter-mapping>

</web-app>

Log4j.properties file which uses the data present in MDC


# sample log4j.properties file, explaining log4j MDC concept
# author: veerasundar.com/blog

log4j.appender.consoleAppender = org.apache.log4j.ConsoleAppender
log4j.appender.consoleAppender.layout = org.apache.log4j.PatternLayout

#note the %X{userName} - this is how you fetch data from Mapped Diagnostic Context (MDC)
log4j.appender.consoleAppender.layout.ConversionPattern = %-4r [%t] %5p %c %x - %m - %X{userName}%n

log4j.rootLogger = DEBUG, consoleAppender

I hope that code explains the concept of MDC. Do let me know if you have any questions/suggestions in the comments.

{ 3 comments… read them below or add one }

diät pillen November 27, 2009 at 4:36 PM

The “Mapped Diagnostic Context” implements a “map” into which key/value pair information can be stored. Just like NDC, the context is stored per thread. Values are stored by key name. Each thread could use the same key name but have different stored values. Values are stored/retreived/removed by using the familiar pattern of MDC.put(), MDC.get(), and MDC.remove() methods.

Reply

Veera November 27, 2009 at 5:18 PM

exactly.

Reply

eiweißpulver December 1, 2009 at 8:22 PM

The NDC and MDC log4j classes are used to store program/application contextual information that can then be used when logging messages. The NDC class name is org.apache.log4j.NDC. “NDC” stands for “Nested Diagnostic Context”. The MDC class name is org.apache.log4j.MDC. “MDC” stands for “Mapped Diagnostic Context”. NDC has been part of the log4j framework longer than MDC. If you haven't already, you may want to review the javadoc information for each class.

Reply

Leave a Comment

You can use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>

Previous post:

Next post: