Hi,
Regarding logging in Digester; I may have found a solution that will
keep all parties happy. Let me know what you think....
Currently this class exists in the plugins module to handle logging:
public class LogUtils {
public static Log getLogger(Digester digester) {
if (digester == null) {
return new org.apache.commons.logging.impl.NoOpLog();
}
return digester.getLogger();
}
}
If it was changed to the code below, promoted to the main digester
package, and used by all code, then:
(a)
For applications which never call Digester.setLogger(...), logging would
be done via different categories, which would make me happy, and
(b)
For applications which call Digester.setLogger(log) things would work as
currently; all logging for all related objects gets redirected to a
single Log object (ie a single category). I think this sucks, but as my
applications don't redirect logging, I don't care.
(c)
It would be 100% backwards-compatible as far as I can see. No API change
occurs on the Digester (users can still call Digester.setLogger as
before). Code which directly accesses
public class LogUtils {
/** default log category is specified string */
public static Log getLogger(Digester digester, String dfltCategory) {
if (digester == null) {
return new org.apache.commons.logging.impl.NoOpLog();
}
else {
Log log = digester.getLogger();
if (log == null) {
log = LogFactory.getLog(dfltCategory)
}
return log;
}
/** default log category is class name */
public static Log getLogger(Digester digester, Class klass) {
...
}
}
As icing on the cake, I suggest the RulesBase class be modified to
manage the log object.
The code below sets the log up as a NoOpLog initially, then when the
digester object is set, it changes the log object to either the
user-specified log object or a log category for the class.
class RulesBase .. {
protected Log log;
public RulesBase() {
log = LogUtils.getLogger(null, this.getClass());
}
public void setDigester(Digester d) {
log = LogUtils.getLogger(d, this.getClass())
}
}
This has a *slightly* different effect from my usual convention of
having a static private Log object on each class; with the code above,
the log category used for logging from inherited methods comes out with
the category of the derived class, not the category of the class on
which the method was actually declared. However that's close enough for
me...
In addition, making the RulesBase object keep track of the log object
means that derived classes are insulated from the actual details of how
the log object is derived. And the implementation is fairly efficient; a
lookup of log object is only done once at construction, and once in
setDigester.
There is a constraint on the above: it is that Digester.setLog must be
called before any objects (such as Rule objects) are added to the
digester. Changing the Log object later may not have the desired effect.
This seems reasonable to me, and may have been the original intention:
it's not explicitly specified, though.
Regards,
Simon
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]