From ff386ee3071c3b6078cd9eaaae9119679dcde16c Mon Sep 17 00:00:00 2001
From: Elliotte Rusty Harold
Warning: implementations for older logging backends such as
- Log4j 1.2,
- Avalon LogKit and
+ Log4j 1.2,
+ Avalon LogKit, and
Lumberjack are also provided, although they are disabled by default.
Familiarity with high-level details of the relevant Logging implementations is presumed.
-As far as possible, JCL tries to be as unobtrusive as possible.
+JCL tries to be as unobtrusive as possible.
In most cases, including the (full)
-Note, however, that if you have a particular preference then providing a simple
+Note, however, that if you have a particular preference, then providing a simple
-When no particular logging library is specified then JCL will silently ignore any logging library
+When no particular logging library is specified, then JCL will silently ignore any logging library
that it finds but cannot initialise and continue to look for other alternatives. This is a deliberate
design decision; no application should fail to run because a "guessed" logging library cannot be
used. To ensure an exception is reported when a particular logging library cannot be used, use one
@@ -163,7 +162,7 @@ to determine what type of
Look for a configuration attribute of this factory named
-
@@ -216,11 +215,11 @@ Configuration of the behavior of the JCL ultimately depends upon the
logging toolkit being used. Please consult the documentation for the chosen logging system.
-JCL is NOT responsible for initialisation, configuration or shutdown of the underlying logging library.
+JCL is NOT responsible for initialisation, configuration, or shutdown of the underlying logging library.
In many cases logging libraries will automatically initialise/configure themselves when first used, and
need no explicit shutdown process. In these situations an application can simply use JCL and not depend
directly on the API of the underlying logging system in any way. However if the logging library being used
-requires special initialisation, configuration or shutdown then some logging-library-specific code will
+requires special initialisation, configuration, or shutdown, then some logging-library-specific code will
be required in the application. JCL simply forwards logging method calls to the correct underlying
implementation. When writing library code this issue is of course not relevant as the calling application
is responsible for handling such issues.
@@ -266,7 +265,7 @@ Note that for application code, declaring the log member as "static" is more
efficient as one Log object is created per class, and is recommended.
However this is not safe to do for a class which may be deployed via a "shared"
classloader in a servlet or j2ee container or similar environment. If the class
-may end up invoked with different thread-context-classloader values set then the
+may end up invoked with different thread-context-classloader values set, then the
member must not be declared static. The use of "static" should therefore
be avoided in code within any "library" type project.
Prior to release 1.0.4, none of the standard Log implementations were
Serializable. If you are using such a release and have a Serializable class
- with a member that is of type Log then it is necessary to declare
+ with a member that is of type Log, then it is necessary to declare
that member to be transient and to ensure that the value is restored on
deserialization. The recommended approach is to define a custom
readObject method on the class which reinitializes that member.commons-logging.jar in the classpath
should result in JCL configuring itself in a reasonable manner.
-There's a good chance that it'll guess (discover) your preferred logging system and you won't
+There's a good chance that it'll guess (discover) your preferred logging system, and you won't
need to do any configuration of JCL at all!
commons-logging.properties file which specifies the concrete logging library to be
used is recommended, since (in this case) JCL will log only to that system
and will report any configuration problems that prevent that system being used.
Log implementation it should use
org.apache.commons.logging.Log (for backwards compatibility to
+org.apache.commons.logging.Log (for backwards compatibility with
pre-1.0 versions of this API, an attribute
org.apache.commons.logging.log is also consulted).
org.apache.commons.logging.Log (for backwards
-compatibility to pre-1.0 versions of this API, a system property
+compatibility with pre-1.0 versions of this API, a system property
org.apache.commons.logging.log is also consulted).
java.logging module is available, use
the corresponding wrapper class
-(Jdk14Logger).
+(Jdk14Logger).
Custom Log implementations not distributed with commons-logging may or may not be Serializable. If you wish your code to be compatible with - any arbitrary log adapter then you should follow the advice given above + any arbitrary log adapter, then you should follow the advice given above for pre-1.0.4 releases.
@@ -340,10 +339,10 @@ In addition to the logging methods, the following are provided for code guards: Thecommons-logging.jar file includes the JCL API, the default
LogFactory implementation and thin-wrapper Log
implementations for
-Log4J,
-Avalon LogKit,
+Log4J,
+Avalon LogKit,
the Avalon Framework's logging infrastructure,
-JDK 1.4, as well as an implementation of JDK 1.4 logging APIs (JSR-47) for
+java.util.logging, as well as an implementation of java.util.logging APIs (JSR-47) for
pre-1.4 systems.
@@ -606,10 +605,10 @@ invokes:
Instead JCL caches the
LogFactory implementation created as a result of the discovery
process and uses the cached factory to return Log objects.
-Since in J2EE and similar multi-classloader environments, the result of the
+Since in JEE and similar multi-classloader environments, the result of the
discovery process can vary depending on the thread context classloader
(e.g. one webapp in a web container may be configured to use Log4j and
-another to use JDK 1.4 logging), JCL internally caches the
+another to use java.util.logging), JCL internally caches the
LogFactory instances in a static hashtable, keyed by classloader.
@@ -624,18 +623,13 @@ classloader (and thus to all the classes loaded by it) will be
held in LogFactory's static hashtable.
-Beginning with JCL 1.1, LogFactory caches factory implementations in a
+LogFactory caches factory implementations in a
"WeakHashtable". This class is similar to java.util.WeakHashMap in
that it holds a WeakReference to each key (but a strong reference
to each value), thus allowing classloaders to be GC'd even if
LogFactory.release() is never invoked.
-Because WeakHashtable depends on JDK 1.3+ features, it is dynamically
-loaded depending on the JVM version; when commons-logging is run on java versions
-prior to 1.3 the code defaults to a standard Hashtable instead.
-
If a custom LogFactory implementation is used, however, then a
WeakHashtable alone can be insufficient to allow garbage collection
of a classloader without a call to release. If the abstract class
@@ -735,8 +729,8 @@ for details.
JCL is distributed with a very simple Log implementation named
org.apache.commons.logging.impl.SimpleLog. This is intended to be a minimal
-implementation and those requiring a fully functional open source logging system are
-directed to Log4J.
+implementation. Developers requiring a fully functional open source logging system are
+directed to Log4J.
SimpleLog sends all (enabled) log messages,