Recipe 17.8 Network Logging with log4j


Problem

You wish to write log file messages using log4j.

Solution

Get a Logger and use its log( ) method or the convenience methods. Control logging by changing a properties file. Make it network-based by using the org.apache.log4j.net package.

Discussion

Logging using log4j is simple, convenient, and flexible. You need to get a Logger object from the static method Logger.getLogger( ) , pass in a configuration identifier that can either be a hierarchical name like com.darwinsys or a Class object (e.g., MyApp.class) that generates the full package and class name. This name can be used in the configuration file to specify the level of detail that you want to see from the logger. The Logger has public void methods debug( ) , info( ), warn( ), error( ) and fatal( ) each of which takes one Object to be logged. As with System.out.println( ), if you pass in anything that is not a String, its toString( ) method is called. A generic logging method is also included:

public void log(Level level, Object message);

The Level class is defined in the log4j package. The standard levels are in this order: DEBUG < INFO < WARN < ERROR < FATAL. So debug messages are least important, and fatal are most important. Each Logger has a level associated with it; messages whose level is less than the Logger's level are silently discarded.

A simple application can log messages using these few statements:

import org.apache.log4j.Logger; import org.apache.log4j.PropertyConfigurator; public class Log4JDemo {     public static void main(String[] args) {         Logger myLogger = Logger.getLogger("com.darwinsys");         Object o = new Object(  );         myLogger.info("I created an object: " + o);     } }

If you compile and run this program with no log4j.properties file, it complains and does not produce any logging output:

ant run.log4jdemo Buildfile: build.xml run.log4jdemo:      [java] log4j:WARN No appenders could be found for logger (com.darwinsys).      [java] log4j:WARN Please initialize the log4j system properly.

So we need to create a configuration file, whose default name is log4j.properties. You can also provide the log file name via System Properties: -Dlog4j.configuration=URL.

Every Logger has a Level to specify what level of messages to write, and an Appender, which is the code that writes the messages out. A ConsoleAppender writes to System.out , of course; other loggers write to files, operating system-level loggers, and so on. A simple configuration file looks something like this:

# Set root logger level to DEBUG and its only appender to APP1. log4j.rootLogger=DEBUG, APP1 # APP1 is set to be a ConsoleAppender. log4j.appender.APP1=org.apache.log4j.ConsoleAppender # APP1 uses PatternLayout. log4j.appender.APP1.layout=org.apache.log4j.PatternLayout log4j.appender.APP1.layout.ConversionPattern=%-4r [%t] %-5p %c %x - %m%n

This file gives the root logger a level of DEBUG write all messages and an appender of APP1, which is configured on the next few lines. Note that I didn't have to refer to the com.darwinsys Logger; since every Logger inherits from the root logger, a simple application needs to configure only the root logger. The properties file can also be an XML document or you can write your own configuration parser (almost nobody does this). With the above file in place, the demonstration works better:

$ ant run.log4jdemo Buildfile: build.xml init: build: run.log4jdemo:      [java] 1    [main] INFO  com.darwinsys  - I created an object: java.lang. Object@bb6086 BUILD SUCCESSFUL Total time: 1 second

A more typical use of logging might be to catch an Exception and log it, as shown in Example 17-12 .

Example 17-12. Log4j catching and logging
import org.apache.log4j.Logger; import org.apache.log4j.PropertyConfigurator; public class Log4JDemo2 {     public static void main(String[] args) {         Logger myLogger = Logger.getLogger("com.darwinsys");         try {             Object o = new Object(  );             if (o != null) {    // bogus, just to show logging                 throw new IllegalArgumentException("Just testing");             }             myLogger.info("I created an object: " + o);         } catch (Exception ex) {             myLogger.error("Caught Exception: " + ex);         }     } }

Much of the flexibility of the log4j package stems from its use of external configuration files; you can enable or disable logging without recompiling the application. A properties file that eliminates all logging might have this entry:

log4j.rootLogger=FATAL, APP1

Only fatal error messages print; all levels less than that are ignored.

To log from a client to a server on a remote machine, the org.apache.log4j.net package includes several Appenders and servers to connect them to.

For more information on log4j, visit http://logging.apache.org/log4j/. log4j is free software, distributed under the Apache Software Foundation license.



Java Cookbook
Java Cookbook, Second Edition
ISBN: 0596007019
EAN: 2147483647
Year: 2003
Pages: 409
Authors: Ian F Darwin

flylib.com © 2008-2017.
If you may any questions please contact us: flylib@qtcs.net