{"record":{"id":"9d37894524a3aa97","repo":"pinojs/pino","slug":"missing-bindings-for-child-pino","errorCode":null,"errorMessage":"missing bindings for child Pino","messagePattern":"missing bindings for child Pino","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"browser.js","lineNumber":208,"sourceCode":"      throw Error('unknown level ' + level)\n    }\n    this._level = level\n\n    set(this, setOpts, logger, 'error') // <-- must stay first\n    set(this, setOpts, logger, 'fatal')\n    set(this, setOpts, logger, 'warn')\n    set(this, setOpts, logger, 'info')\n    set(this, setOpts, logger, 'debug')\n    set(this, setOpts, logger, 'trace')\n\n    customLevels.forEach((level) => {\n      set(this, setOpts, logger, level)\n    })\n  }\n\n  function child (setOpts, bindings, childOptions) {\n    if (!bindings) {\n      throw new Error('missing bindings for child Pino')\n    }\n    childOptions = childOptions || {}\n    if (serialize && bindings.serializers) {\n      childOptions.serializers = bindings.serializers\n    }\n    const childOptionsSerializers = childOptions.serializers\n    if (serialize && childOptionsSerializers) {\n      var childSerializers = Object.assign({}, serializers, childOptionsSerializers)\n      var childSerialize = opts.browser.serialize === true\n        ? Object.keys(childSerializers)\n        : serialize\n      delete bindings.serializers\n      applySerializers([bindings], childSerialize, childSerializers, this._stdErrSerialize)\n    }\n    function Child (parent) {\n      this._childLevel = (parent._childLevel | 0) + 1\n\n      // make sure bindings are available in the `set` function","sourceCodeStart":190,"sourceCodeEnd":226,"githubUrl":"https://github.com/pinojs/pino/blob/5aa62305c57709ebd6f6b7c328e8830eeb29b297/browser.js#L190-L226","documentation":"pino().child() requires a bindings object as its first argument. The browser build's child function (browser.js:208) throws immediately when bindings is falsy because a child logger must inherit at least an empty set of bindings to derive its identity.","triggerScenarios":"Calling logger.child() with no arguments, or explicitly with undefined/null as the first argument, e.g. logger.child().","commonSituations":"Migrating from other logging libraries (like winston's child or custom factories) that allow argument-less child(); refactoring code that removed bindings but left the child() call; forgetting to pass { reqId } style context.","solutions":["Pass a bindings object as the first argument, even if empty: logger.child({})","Move any contextual fields (requestId, module name) into the bindings object","If you intended to pass only childOptions, pass bindings first: logger.child({}, childOptions)"],"exampleFix":"// before\nconst child = logger.child();\n// after\nconst child = logger.child({ module: 'payments' });","handlingStrategy":"validation","validationCode":"function safeChild(logger, bindings) {\n  if (bindings == null || typeof bindings !== 'object') {\n    throw new TypeError('child() requires a bindings object');\n  }\n  return logger.child(bindings);\n}","typeGuard":"function hasBindings(b) { return typeof b === 'object' && b !== null; }","tryCatchPattern":"try { const child = logger.child(bindings); } catch (e) { if (e.message === 'missing bindings for child Pino') { child = logger.child({}); } else { throw e; } }","preventionTips":["Always pass an object to child(), even when there is nothing to bind: child({})","Wrap logger.child in a factory helper that enforces the bindings argument","Enable lint rules or code review checks for child() calls with zero arguments"],"tags":["logging","api-misuse","pino","browser"],"backgroundTag":"missing-required-argument","analyzedSha":"5aa62305c57709ebd6f6b7c328e8830eeb29b297","analyzedAt":"2026-09-02T22:05:21.418Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-10T02:17:09.455Z"}