RFR 2: JDK-8005263: Logging APIs takes Supplier for message (original) (raw)

Peter Levart peter.levart at gmail.com
Fri Dec 28 00:42:21 UTC 2012


What about the following API:

public class LogRecordFactory {

 private final Level level;

 public LogRecordFactory(Level level) {
     this.level = level;
 }

 public LogRecord create(String msg) {
     return new LogRecord(level, msg);
 }

 public LogRecord create(String msg, Object... parameters) {
     LogRecord lr = create(msg);
     lr.setParameters(parameters);
     return lr;
 }

 // ...etc...

}

and then in the Logger...

 public void log(Level level, Function<LogRecordFactory, LogRecord> 

logRecordProducer) { if (level.intValue() < levelValue || levelValue == offValue) { return; } LogRecord lr = logRecordProducer.apply(new LogRecordFactory(level)); doLog(lr); }

which would be used as:

     logger.log(Level.INFO, lrp -> lrp.create("Status is: %s", 

getStatus()));

Regards, Peter

On 12/27/2012 01:23 AM, Henry Jen wrote:

On 12/22/2012 07:30 AM, Jason Mehrens wrote:

The msg argument in most cases is a string literal because it is either a resource bundle key or a MessageFormat literal. The established best practice is to convert on the fly construction of messages to use the MessageFormat syle logging. This current patch is kind of anti-pattern of that practice. I would think the real win would be to delay construction of the 'params' argument in the logging framework. Allowing the callers to write logger.log(level, "{0}", Foo::bar) and have the call to bar be lazy eval would be the best of both the logging world and the lambda world.

For messages not just only for developer, they should be localized as you suggested and in such cases, it is possible to achieve the laziness via Object.toString(), less straightforward than using a lambda, but is possible. Cheers, Henry



More information about the core-libs-dev mailing list