-
Notifications
You must be signed in to change notification settings - Fork 63
ReplaceAttrs incompatible with slog #41
Description
I found two things that tint does different to slog, which makes Options not quite a drop-in replacement for slog.HandlerOptions:
First, slog calls Resolve before ReplaceAttr, as documented:
ReplaceAttr is called to rewrite each non-group attribute before it is logged. The attribute's value has been resolved (see [Value.Resolve]).
tint calls Resolve after ReplaceAttr.
Second, tint does not call ReplaceAttr recursively for groups. With the tint handler, slog.Info("foo", slog.Group("bar", "x", "y")) causes a call to ReplaceAttr with an empty groups argument and slog.GroupValue("bar", "x", "y"). slog's handlers instead call ReplaceAttr with []string{"bar"}, slog.Attr{Key:"x", Value: slog.StringValue("y")}.
The documentation on slog.HandlerOptions.ReplaceAttr reads
ReplaceAttr is never called for Group attributes, only their contents.
The two things together interact surprisingly in slog in Go 1.21.1. With a value that Resolves to a GroupValue, slog does call ReplaceAttr with the Group attribute (and after that once for each member of the group). This is either a bug in the implementation or the docs. I opened golang/go#62731 about this. Maybe keep an eye on that.