pino icon indicating copy to clipboard operation
pino copied to clipboard

Access to child object in logMethod

Open kevinsimper opened this issue 4 years ago • 6 comments

I was looking to access the child object, I want to make so that it prepends the message object.

Here I log what inputArgs contains inside hooks.logMethod

after having called logger.child({"featureName":"MY FEATURE"}

{ inputArgs: [ 'special' ] }
{"level":30,"time":1597765635449,"featureName":"MY FEATURE","message":"special"}

I am trying to make a function that will prepend that name to message, so it becomes

{"level":30,"time":1597765635449,"featureName":"MY FEATURE","message":"MY FEATURE: special"}

kevinsimper avatar Aug 18 '20 15:08 kevinsimper

The hook has no way of obtaining that context:

https://github.com/pinojs/pino/blob/95856d1198a4067f9916a2b7e636b71f58bebeb2/lib/tools.js#L30-L35

jsumners avatar Aug 18 '20 16:08 jsumners

Is not this?

mcollina avatar Aug 18 '20 16:08 mcollina

Is not this?

Maybe? I think bindings are rendered to a string at child creation.

jsumners avatar Aug 18 '20 16:08 jsumners

Is there anywhere to obtain the "parent" binding context? I have tried pretty much every hook/method and can't find a way to access the context before the new bindings are written. It would be nice to have some way to designate that child loggers are children of other loggers, for example to append the log name:

const log = logger.child({ name: 'app' });
const log2 = log.child({ name: `service` });
// via hook or formatter set log2's name to "app:service"

This would also allow easy filtering of logs in logMethod to mirror debug filtering:

function logMethod(this: any, inputArgs: any, method: pino.LogFn) {
  // Check child against debug variable
  const { name } = this.bindings();
  if (!debug.enabled(name)) return;
  return method.apply(this, inputArgs);
}

I initially assumed this could be done via formatters.bindings but it doesn't have access to the logger instance and (this might be a bug) it is only run during pino instance creation and NOT during subsequent child calls... which is how it is stated in the documentation

danielmahon avatar Feb 01 '21 17:02 danielmahon

Best way I've found so far is to wrap the logger.child method:

const defaultChildMethod = logger.child;
logger.child = function child(newBindings) {
  const { name } = this.bindings();
  const newName = newBindings.name;
  if (name && newName) {
    newBindings.name = `${name}:${newName}`;
  }
  return defaultChildMethod.apply(this, [newBindings]);
};

danielmahon avatar Feb 01 '21 19:02 danielmahon

I think we should extend formatters.bindings so that it forward this to the current logger.

https://github.com/pinojs/pino/blob/185dc159166d8d31471a31532fede220d5a8d588/lib/tools.js#L157

Could you send a PR?

mcollina avatar Feb 02 '21 08:02 mcollina