From c77556bda2ae3f68b6ccac360130f5d1942bd4b2 Mon Sep 17 00:00:00 2001 From: Evan Phoenix Date: Thu, 16 Mar 2023 14:57:20 -0700 Subject: [PATCH] Add ability to wrap new subloggers SubloggerHook is a function that when defined, is passed any new sublogger that is created. This allows hclog users to wrap any sublogger in similar functionality as the original, as well as adjust any sublogger parameters dynamically. --- intlogger.go | 17 ++++++++++++++--- logger.go | 7 +++++++ 2 files changed, 21 insertions(+), 3 deletions(-) diff --git a/intlogger.go b/intlogger.go index b61476b..26f887a 100644 --- a/intlogger.go +++ b/intlogger.go @@ -85,6 +85,8 @@ type intLogger struct { // create subloggers with their own level setting independentLevels bool + + subloggerHook func(sub Logger) Logger } // New returns a configured logger. @@ -151,6 +153,7 @@ func newLogger(opts *LoggerOptions) *intLogger { independentLevels: opts.IndependentLevels, headerColor: headerColor, fieldColor: fieldColor, + subloggerHook: opts.SubloggerHook, } if opts.IncludeLocation { l.callerOffset = offsetIntLogger + opts.AdditionalLocationOffset @@ -166,6 +169,10 @@ func newLogger(opts *LoggerOptions) *intLogger { l.timeFormat = opts.TimeFormat } + if l.subloggerHook == nil { + l.subloggerHook = identityHook + } + l.setColorization(opts) atomic.StoreInt32(l.level, int32(level)) @@ -173,6 +180,10 @@ func newLogger(opts *LoggerOptions) *intLogger { return l } +func identityHook(logger Logger) Logger { + return logger +} + // offsetIntLogger is the stack frame offset in the call stack for the caller to // one of the Warn, Info, Log, etc methods. const offsetIntLogger = 3 @@ -774,7 +785,7 @@ func (l *intLogger) With(args ...interface{}) Logger { sl.implied = append(sl.implied, MissingKey, extra) } - return sl + return l.subloggerHook(sl) } // Create a new sub-Logger that a name decending from the current name. @@ -788,7 +799,7 @@ func (l *intLogger) Named(name string) Logger { sl.name = name } - return sl + return l.subloggerHook(sl) } // Create a new sub-Logger with an explicit name. This ignores the current @@ -799,7 +810,7 @@ func (l *intLogger) ResetNamed(name string) Logger { sl.name = name - return sl + return l.subloggerHook(sl) } func (l *intLogger) ResetOutput(opts *LoggerOptions) error { diff --git a/logger.go b/logger.go index 7e08aa6..0194603 100644 --- a/logger.go +++ b/logger.go @@ -299,6 +299,13 @@ type LoggerOptions struct { // logger will not affect any subloggers, and SetLevel on any subloggers // will not affect the parent or sibling loggers. IndependentLevels bool + + // SubloggerHook registers a function that is called when a sublogger via + // Named, With, or ResetNamed is created. If defined, the function is passed + // the newly created Logger and the returned Logger is returned from the + // original function. This option allows customization via interception and + /// wrapping of Logger instances. + SubloggerHook func(sub Logger) Logger } // InterceptLogger describes the interface for using a logger