zitadel/zitadel · error
unable to set logger: %w
Error message
unable to set logger: %w
What it means
cmd/ready's newConfig wraps any failure from config.Log.SetLogger() with "unable to set logger: %w". The ready command needs a working logger before it runs health probes; if the legacy logger cannot be constructed from the config (logging config invalid, sink not writable, formatter misconfigured), startup aborts with this wrapper. The underlying cause is always in the wrapped error.
Source
Thrown at cmd/ready/config.go:47
viper.DecodeHook(mapstructure.ComposeDecodeHookFunc(
hook.Base64ToBytesHookFunc(),
mapstructure.StringToTimeDurationHookFunc(),
mapstructure.StringToTimeHookFunc(time.RFC3339),
mapstructure.StringToSliceHookFunc(","),
hook.EnumHookFunc(internal_authz.MemberTypeString),
mapstructure.TextUnmarshallerHookFunc(),
)),
)
if err != nil {
return nil, nil, fmt.Errorf("unable to read default config: %w", err)
}
// Force-disable metrics and tracing for ready command
config.Instrumentation.Metric.Exporter.Type = instrumentation.ExporterTypeNone
config.Instrumentation.Trace.Exporter.Type = instrumentation.ExporterTypeNone
// Legacy logger
err = config.Log.SetLogger()
if err != nil {
return nil, nil, fmt.Errorf("unable to set logger: %w", err)
}
shutdown, err := instrumentation.Start(cmd.Context(), config.Instrumentation)
if err != nil {
return nil, nil, fmt.Errorf("unable to start instrumentation: %w", err)
}
cmd.SetContext(logging.NewCtx(cmd.Context(), logging.StreamRuntime))
return config, shutdown, nil
}
View on GitHub (pinned to 13948f2bcd)
Solutions
- Read the wrapped %w cause in the error output; fix the specific logger config problem it names.
- Validate the Log section in config.yaml / ZITADEL_LOG* env vars (valid level, formatter, sink).
- Run with default logging (remove custom Log overrides) to confirm the custom config is the culprit.
Example fix
// before (config.yaml) Log: Level: verbosedebug // after Log: Level: debug
Defensive patterns
Strategy: validation
Validate before calling
cfg, _ := readConfig()
if cfg.Log.Level == "" || !isValidLogLevel(cfg.Log.Level) {
return fmt.Errorf("invalid log level %q", cfg.Log.Level)
} Try / catch
if err := config.Log.SetLogger(); err != nil {
return fmt.Errorf("unable to set logger: %w", err)
} Prevention
- Keep Log config minimal; only override level/formatter when needed.
- Validate config.yaml with `zitadel setup --config` dry runs before automating ready.
- Pin valid values for ZITADEL_LOG_LEVEL / ZITADEL_LOG_FORMATTER in your deployment env.
When it happens
Trigger: Running `zitadel ready` with a Log config section that SetLogger() rejects — e.g. an invalid log level, unsupported formatter in LogSlog/legacy config, or a log destination that cannot be opened.
Common situations: Misquoted or invalid YAML in the Log section of config.yaml; ZITADEL_LOG_* env vars set to invalid values; running ready in a container where the configured log file path is not writable.
Understand the failure class
Background: "Invalid value" and "allowed values are" config errors: what your library rejected and how to fix it — this error's family across 41 libraries.
Related errors
- unable to set logger: %w
- masterkey must either be provided by file path, value or env
- unable to set logger: %w
- unable to start instrumentation: %w
- unable to read config: %w
AI-assisted analysis of zitadel/zitadel@13948f2bcd (2026-09-06).
Data as JSON: /api/errors/80b58d3cc53b4032.
Report an issue: GitHub.