Config.Logger is a *slog.Logger. The nexus.Logger interface and NoopLogger are gone.
Logger discards everything.
Why *slog.Logger
log/slog is the standard library’s structured logger and the ecosystem has settled on
its Handler interface, so accepting a *slog.Logger reaches every backend without the
SDK depending on any of them. zap, zerolog and logrus all provide a handler, and so does
anything else worth using.
It also makes the output aggregatable. Values arrive as attributes rather than baked
into the message text, so every occurrence of an event shares one message template:
“how often did the stream drop” becomes a countable query rather than a substring search
over lines that are each slightly different.
What the output looks like
component attribute naming the subsystem:
So the three can be routed or filtered independently without parsing message text.
Levels
Nothing above
Error is ever emitted: the SDK does not decide that an application
should stop.
Scoping the SDK’s output
Pass a logger that already carries attributes of your own and everything the SDK emits inherits them:Secrets never appear
Secret values are never logged, as a message or as an attribute, and neither are secret key names. The same holds for the API key, the workload OIDC token and the session JWT. A test drives a sync carrying both a text and a file-type secret through a capturing handler at debug level and fails if any of them shows up in the output, so this is a checked property rather than a convention.Observer faults
AStreamObserver callback that panics is recovered, and the fault is
reported here at Error with the hook name and a stack trace:
