gohugoio/hugo · error
failed to decode media types: %w
Error message
failed to decode media types: %w
What it means
This is the wrapping error returned when Hugo fails to decode the contentTypes config namespace. The underlying cause (%w) is either a structural decode failure (the section isn't a map, or a value can't be weak-decoded into ContentTypeConfig) or the 'unknown media type' validation error from the same buildConfig function. It surfaces at config load, halting the build.
Source
Thrown at media/config.go:216
}
}
for k := range s {
mediaType, found := types.GetByType(k)
if !found {
return c, nil, fmt.Errorf("unknown media type %q", k)
}
c.types = append(c.types, mediaType)
}
c.init(types)
return c, s, nil
}
ns, err := config.DecodeNamespace[map[string]ContentTypeConfig](in, buildConfig)
if err != nil {
return nil, fmt.Errorf("failed to decode media types: %w", err)
}
return ns, nil
}
// DecodeTypes decodes the given map of media types.
func DecodeTypes(in map[string]any) (*config.ConfigNamespace[map[string]MediaTypeConfig, Types], error) {
buildConfig := func(v any) (Types, any, error) {
m, err := hmaps.ToStringMapE(v)
if err != nil {
return nil, nil, err
}
if m == nil {
m = map[string]any{}
}
m = hmaps.CleanConfigStringMap(m)
// Merge with defaults.
hmaps.MergeShallow(m, defaultMediaTypesConfig)
View on GitHub ↗ (pinned to 8a468df065)
Solutions
- Read the wrapped error after the colon — it names the exact cause (often 'unknown media type ...') and fix that.
- Ensure contentTypes is a map of MIME-string keys to tables, matching the documented shape.
- Validate the merged config with 'hugo config' to spot values injected by themes or modules.
Example fix
# before (hugo.yaml)
contentTypes: text/markdown
# after
contentTypes:
text/markdown: {} Defensive patterns
Strategy: try-catch
Validate before calling
// Ensure mediaTypes config values are tables/maps, not scalars
for k, v := range cfg.GetStringMap("mediaTypes") {
if _, ok := v.(map[string]any); !ok {
return fmt.Errorf("mediaTypes.%s must be a table, got %T", k, v)
}
} Try / catch
conf, err := allconfig.LoadConfig(...)
if err != nil {
// wrapped error chain: use errors.Unwrap / %+v to find the offending key
log.Fatalf("config decode failed: %+v", err)
} Prevention
- Keep mediaTypes entries as tables with known keys (suffixes, delimiter) only
- Validate TOML/YAML syntax with a linter before running hugo
- Unwrap the %w chain to find the exact malformed field instead of guessing
When it happens
Trigger: config.DecodeNamespace failing while building ContentTypes: passing a non-map value for contentTypes, a value that mapstructure.WeakDecode cannot coerce into ContentTypeConfig, or an unregistered media-type key (which produces error 391 as the wrapped cause).
Common situations: Malformed contentTypes section in hugo.toml/yaml/json (e.g. a string or array where a table/map is expected); wrong nesting of keys; unknown media type keys; merging config from themes/modules where types conflict.
Related errors
- failed to decode config for language %q: %w
- failed to decode %q: %w
- unknown media type %q
- language %q not found
- unsupported format: %q
AI-assisted analysis of gohugoio/hugo@8a468df065 (2026-07-31).
Data as JSON: /data/errors/943a3c6ae15c4006.json.
Report an issue: GitHub ↗.