Ceki,

I'm not sure I understand very well this. 

I think we have a consensus on few items ( and you seem to just repeat 
them ):

- JDK1.4 logging is not useable as a 'standard logging API' ( even if it 
is released under JCP )

- log4j is the best logger ( for Peter and few others: logkit is the best 
logger, and I doubt too many people will argue that JDK1.4 logging is the 
best ). The consensus here is that everyone has a favorite logger 
implementation. 

- there are other logger implementations in use - JDK1.4, logkit, log4j, 
probably many others ( for example tomcat3.3 and tomcat4.0 each has a 
logger ).

- it is better for a user program to code using a single API and beeing 
able to choose the implemntation.

The commons-logging API is implementable by each logger, and it's the 
closest to a 'standard API for logging' that you can get. 

If the wrapping performance worries you - there's a very simple solution, 
at your disposal - just make log4j.Logger implement commons.Logger, 
create and maintain a log4j factory that is consistent with the rest of 
log4j and you'll have no wrapper :-)

With the current discovery mechnism, if you implement commons-logger 
factory and include the manifest entry in log4j, it'll automatically be 
used ( instead of the wrapper ). 

Replacing the package name is a silly sugestion - you realize most people 
want to release a single package and have it work, you can't ask the 
user to do a replace and recompile if they want a different logger.
 
The goal is not to be able to change the logger at compile time, but to be 
able to detect the platform logger and use it. The only way to do that is 
via a standard API - and commons-logging seems to be the only standard for 
logging that we have, supported ( mostly unwillingly :-) on all logging 
implementations. If you are concerned about the user experience with 
commons-logging and log4j, the best way to resolve that is by 
participating in commons-logging and implementing it in log4j so that 
log4j will work best with commons-logging.


Costin


On Wed, 27 Mar 2002, Ceki Gülcü wrote:

> 
> Hello all,
> 
> Given that log4j is such a low-level library, most organizations are
> suspicious to tie their code to log4j, especially considering the new
> logging API in JDK 1.4.
> 
> Before going forward, it is appropriate to mention that these two APIs
> are very similar.  The classical usage pattern for log4j is:
> 
> ---------------------------------------------------------------
> 
> import org.apache.log4j.Logger;
> 
> public class MyClass {
>    final static Logger logger = Logger.getLogger("some.name");
> 
>     public void foo1() {
>       logger.debug("Hello world.");
>     }
> 
>     public void foo2() {
>       logger.info("Another message.");
>       logger.error("Stop that!", new Exception("The earth is getting 
> warmer."));
>     }
> }
> ---------------------------------------------------------------
> 
> As you are well aware by now, one of the important benefits of log4j
> is that it can be configured at run time using configuration scripts.
> You can have hundreds or thousands of log statement but only one or
> two lines of code to configure log4j.
> 
> The usage pattern for the JDK 1.4 logging API is:
> 
> ---------------------------------------------------------------
> import java.util.logging.Logger;
> 
> public class MyClass {
>     final static Logger logger = Logger.getLogger("test");
> 
>     public void foo1() {
>       logger.debug("Hello world.");
>     }
> 
>     public void foo2() {
>       logger.info("Another message.");
>       logger.error("Stop that!", new Exception("The earth is getting 
> warmer."));
>     }
> }
> ---------------------------------------------------------------
> 
> Do you notice anything similar? The JDK 1.4 logging API also admits
> configuration scripts. Being part of the JDK, the common guess that
> this API will supplant log4j some time in the future.
> 
> It is not so easy to write a complete logging API. Users
> come to realize they need the features present in log4j but absent in
> JDK 1.4 logging API.  Moreover, log4j runs with JDK 1.1 or later whereas
> the JDK 1.4 logging API, requires, well, JDK 1.4.  Most users can't
> afford to tie their code to JDK 1.4.
> 
> But they need logging and they need it now. A common strategy for
> protecting against future changes and at the same time to benefit from
> existing log4j features is to *wrap* log4j with a custom logging
> API. Log4j actually has support to facilitate such wrappers.
> 
> It turns out that such wrappers are not that trivial to write. I frequently
> receive email where a user runs into a problem with their wrapper and
> requests help. More often than not, these wrappers are of poor quality
> such that the cost of inactive (or disabled) logging statements is
> multiplied by a factor of 1'000.
> 
> Of course, not all wrappers are of poor quality. For example, the
> commons-logging API is rather well implemented. Obviously, there is
> still a cost for the wrapping but it won't be of a huge factor.
> 
> The commons-logging API will try to use the JDK 1.4 API if present, or
> the log4j API. The *current* preference is log4j I believe. Neat!
> 
> Now, it just happens that the part where most users have difficulty is the
> initialization of the log4j API. Where should the log4j.jar go? Where
> do I put the log4j.properties files?  Can I have different
> web-applications have different log4j configurations?  How do I
> initialize log4j in an application server?  Although there is ample
> literature on the subject, much confusion remains.
> 
> The commons-logging API as it wraps multiple logging APIs such
> as Avalon's LogKit, log4j, JDK 1.4 has its own "discovery process".
> Things were confusing before, they will be even more when
> commons-logging API enters "common" usage. With some effort, it might
> start making sense to you. However, your users will not show the same
> perseverance nor enthusiasm.
> 
> There will be also unexpected interactions between log4j and the
> commons-logging API. For example, log4j 1.2alpha1 through alpha4 had a
> very subtle bug which caused client code compiled with log4j version
> 1.1.3 to throw exceptions when ran with log4j 1.2alpha. Inversely,
> code compiled with 1.2alpha would crash when ran using log4j 1.1.3.
> This problem was fixed in log4j beta.
> 
> It is now sufficient for client code to be compiled with 1.1.x and to
> run with 1.2 beta without problems and vice versa. Of course if
> commons-logging compiled with log4j 1.2alpha the problem would be
> sticky. It would not go away by compiling client code but only by replacing
> the commons-logging API.
> 
> In the recent weeks I have also started to receive disturbing bug reports
> where components using commons-logging API behave strangely.
> 
> http://nagoya.apache.org/bugzilla/show_bug.cgi?id=7484
> http://nagoya.apache.org/bugzilla/show_bug.cgi?id=6764
> 
> I suspect that these problems will only worsen in the future. The
> commons-logging developers will suspect a log4j bug and we will
> suspect a commons-logging API bug. By increasing the number of
> components required for logging you have doubled the probability of
> bugs while the difficulty of resolving them has increased by a higher
> multiple.
> 
> Remember that the initial goal of introducing a wrapper API was to
> protect our coding investment. If for whatever reason you decide to
> drop log4j in favor of JDK 1.4 (or the other way around) a simple
> string search-and-replace operation will do. Most IDEs support
> search-and-replace operations on multiple files. All you have to do is
> to replace "import org.apache.log4j.Logger" with "import
> java.util.logging.Logger".
> 
> I believe the saying is "a penny today is worth a promise of a nickel
> tomorrow." By adopting a wrapper API, you are trading "a nickel of
> today for a promise of a penny tomorrow."
> 
> As long as you are aware that the supposedly free-lunch may turn out
> to be an expensive and not so tasty meal after all...
> 
> 
> --
> Ceki
> My link of the month: http://java.sun.com/aboutJava/standardization/
> 
> 
> --
> To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
> For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>
> 
> 


--
To unsubscribe, e-mail:   <mailto:[EMAIL PROTECTED]>
For additional commands, e-mail: <mailto:[EMAIL PROTECTED]>

Reply via email to