On May 22, 2010, at 8:13 PM, Curt Arnold wrote:

> 
> On May 22, 2010, at 10:50 AM, Ralph Goers wrote:
>> 
>>> 
>>> Also, I have had an issue where the I wanted the toString() method on the 
>>> object to be logged to be delayed as much as possible (somewhat helped with 
>>> the {}-construct in slf4j).  This might be doable with a specific log 
>>> interface.
>> 
>> That is exactly what Message does.
>> 
> 
> 
> My thoughts, but not sure how much of this got into my earlier code, was to 
> have a distinct extraction phase that occur synchronously with the logging 
> call that would extract all info needed for a completion phase that could 
> occur either immediately or be deferred.  The extraction phase would need to 
> extract any info from the call into immutable objects so state change, for 
> example mutable message parameters, before the completion stage would not 
> change the resulting log.

There is no point in doing this in simple use cases such as using the 
FileAppender to write to a log file.

> 
> A example where this would be useful is logging floating point numbers.  It 
> can be surprisingly expensive to format floating point numbers, so it is 
> highly beneficial to extract all the pieces needed for the formatting into an 
> immutable package during the synchronous extraction phase and then do the 
> formatting in the asynchronous completion phase.

This assumes there is an asynchronous phase. In my audit logging use cases I do 
not want asynchronous logging because I want any exceptions that occur to be 
thrown back to the caller.  An awful lot of logs just write Strings and simple 
values. While we should support use cases like what you are suggesting I think 
it would be unwise to optimize for them at the expense of typical usage.

> 
> The AsynchronousAppender in log4j requires trying to freeze LoggingEvent 
> which is still subject to message objects changing underneath it.  Also it 
> generally perform unnecessary actions in freezing everything in the 
> LoggingEvent even though much of it will not be used.
> 
> The framework should be designed to separate the parts required to be 
> synchronous (that is anything dealing with external objects) from the parts 
> that can be deferred. 

I don't think I really agree with this, at least the way you are expressing it. 
Typically, the "parts required to be synchronous" are also the ones that are 
expensive to resolve. What you are suggesting is that somehow it is easier to 
deal with a LogEvent that has a reference to another object that contains the 
references to the "synchronous objects" than to just copy the whole LogEvent. 
But copying simple object references like Strings doesn't cost all that much 
and may not even be worth doing if the appender needs some sort of serialized 
version of the LogEvent instead (SyslogAppender using either the serialized 
logging event or the IETFSyslogLayout that I haven't added yet).

In looking at Log4jLogEvent really the only fields that deal with external 
objects are the Message and the Throwable.  I suppose a Throwable could be a 
problem if the caller has created their own exception type and added odd stuff 
to it (complex object references), although I can't say I've ever run across an 
Exception that does that.  The Message can be solved by a) doing new 
SimpleMessage(message.getFormattedMessage()), b) serializing the message and 
deserializing it, or c) adding another method to the Message interface like 
"prepareForAsynch". 



Ralph
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to