Skip to content

Error Handling

Confii returns structured *confii.ConfigError values for configuration failures. The structure separates a stable machine-readable category from the concrete operational cause and operator-facing message.

value, err := cfg.Get("database.host")
if err != nil {
    if errors.Is(err, confii.ErrConfigNotFound) {
        // Handle a missing key without parsing the message.
    }

    var configErr *confii.ConfigError
    if errors.As(err, &configErr) {
        slog.Error("configuration operation failed",
            "operation", configErr.Op,
            "code", configErr.Code,
            "source", configErr.Source,
            "key", configErr.Key,
        )
    }
}

Stable categories

ConfigError.Code uses ConfigErrorCode. Each code corresponds to a sentinel accepted by errors.Is:

Code Sentinel Meaning
config_load ErrConfigLoad Source loading, initialization, or materialization failed
config_format ErrConfigFormat A source format or declared format/path combination is invalid
config_validation ErrConfigValidation The candidate failed schema, typed, or custom validation
config_not_found ErrConfigNotFound A requested key does not exist
config_merge ErrConfigMerge Configuration values cannot be merged under the selected strategy
config_frozen ErrConfigFrozen A mutation was attempted after freezing
config_closed ErrConfigClosed A mutation was attempted after closing
config_access ErrConfigAccess A value cannot be returned as the requested access type
config_invalid ErrConfigInvalid An operation argument or mutation path is invalid

Use errors.Is for control flow and ConfigError.Code for structured logging, telemetry, or transport. Do not compare Error() strings; they are intended for operators and may gain additional context.

Concrete causes and diagnostic context

ConfigError.Err is the single wrapped operational cause. Standard errors.Is and errors.As traversal can therefore find context cancellation, deadlines, filesystem failures, SDK errors, and application validator errors.

ConfigError.Context contains bounded, structured diagnostic data. For example, key-not-found errors retain the complete available_keys slice even though the rendered message limits the list. Validation errors similarly keep structured violations without embedding configuration values in the message.

Inspection and export failures

Inspection APIs use the same contract as loading, access, and mutation APIs:

Failure Category Structured fields
Nil target passed to Diff config_invalid Op: "Diff"
Unsupported GenerateDocs or Export format config_invalid Op and Context["format"]
Documentation encoding or exporter failure config_access Op, format context, and wrapped cause
Export or debug-report write failure config_access Op, output path in Source, and wrapped filesystem cause

When serialization succeeds but writing an export file fails, Export returns both the serialized bytes and the structured write error. This lets callers recover or redirect the already-produced sensitive output without retrying the exporter. The returned bytes can contain resolved secrets and must be handled accordingly.