gohugoio/hugo · error
type %T not supported
Error message
type %T not supported
What it means
Thrown by transform.Unmarshal (tpl/transform/unmarshal.go:121) in the non-Resource code path after types.ToStringE(data) fails. Unmarshal only accepts data that is a string, []byte, json.RawMessage, or an UnmarshableResource; any other Go type reaches this branch. The %T prints the offending concrete type so the developer can see exactly what was passed.
Source
Thrown at tpl/transform/unmarshal.go:121
return &resources.StaleValue[any]{
Value: v,
StaleVersionFunc: func() uint32 {
return resource.StaleVersion(r)
},
}, nil
})
if err != nil {
return nil, err
}
return v.Value, nil
}
dataStr, err := types.ToStringE(data)
if err != nil {
return nil, fmt.Errorf("type %T not supported", data)
}
if strings.TrimSpace(dataStr) == "" {
return nil, nil
}
key := hashing.XxHashFromStringHexEncoded(dataStr)
if decoder != metadecoders.Default {
key += decoder.OptionsKey()
}
v, err := ns.cacheUnmarshal.GetOrCreate(key, func(string) (*resources.StaleValue[any], error) {
var f metadecoders.Format
if decoder.Format != "" {
f = metadecoders.FormatFromString(decoder.Format)
if f == "" {
return nil, fmt.Errorf("format %q not supported", decoder.Format)View on GitHub (pinned to 52c9bd7908)
Solutions
- Coerce the value to a string before unmarshaling: {{ transform.Unmarshal (string $value) }}
- Pass a Resource obtained via resources.Get / .Resources instead of a raw value
- If the value is already a map/slice, use it directly instead of re-unmarshaling
- In Go, assert resource.UnmarshableResource or string/[]byte before calling ns.Unmarshal
Example fix
// before
{{ transform.Unmarshal $param }}
// after
{{ transform.Unmarshal (string $param) }} Defensive patterns
Strategy: validation
Validate before calling
// In Go: check the data type before calling Unmarshal.
switch v := data.(type) {
case string, []byte, json.RawMessage:
// safe
resource.UnmarshableResource:
// safe
default:
s, err := types.ToStringE(v)
if err != nil {
return fmt.Errorf("convert data to string before Unmarshal: %w", err)
}
data = s
}
// In templates: {{ transform.Unmarshal (string $value) }} Prevention
- Always stringify non-resource values before transform.Unmarshal
- Prefer passing a Resource over raw values for typed data
- Use printf "%T" to log the type when debugging template data flow
When it happens
Trigger: Calling {{ transform.Unmarshal $value }} (or the Go Namespace.Unmarshal) where $value is an int, bool, struct, map, or slice that is neither string-convertible nor a resource.UnmarshableResource. Common: piping a .Param that resolves to a number or array, or an .Scratch value holding a non-string type.
Common situations: Passing already-decoded data (a map from a data file) back into Unmarshal; piping a resource object that does not implement UnmarshableResource; passing front-matter values of unknown type straight from .Params.
Related errors
- unknown format
- failed to decode options: %w
- format %q not supported
- MIME %q not supported
- invalid character: %q
AI-assisted analysis of gohugoio/hugo@52c9bd7908 (2026-08-09).
Data as JSON: /api/errors/44b2b70b0be72bb3.
Report an issue: GitHub.