lima-vm/lima · error
failed to marshal as YAML: %+v: %w
Error message
failed to marshal as YAML: %+v: %w
What it means
The "yaml" template function encodes its argument with goccy/go-yaml and panics if the encoder fails, wrapping the value and underlying error. The panic propagates through text/template execution, aborting template rendering. YAML marshaling of plain Go data rarely fails, but goccy/go-yaml enforces type constraints (e.g. unsupported map key types, invalid values for time/encoding) that trigger this.
Source
Thrown at pkg/textutil/textutil.go:70
return text
}
// TemplateFuncMap is a text/template FuncMap.
var TemplateFuncMap = template.FuncMap{
"json": func(v any) string {
var b bytes.Buffer
enc := json.NewEncoder(&b)
enc.SetEscapeHTML(false)
if err := enc.Encode(v); err != nil {
panic(fmt.Errorf("failed to marshal as JSON: %+v: %w", v, err))
}
return strings.TrimSuffix(b.String(), "\n")
},
"yaml": func(v any) string {
var b bytes.Buffer
enc := yaml.NewEncoder(&b)
if err := enc.Encode(v); err != nil {
panic(fmt.Errorf("failed to marshal as YAML: %+v: %w", v, err))
}
return "---\n" + strings.TrimSuffix(b.String(), "\n")
},
"indent": func(a ...any) (string, error) {
if len(a) == 0 {
return "", errors.New("function takes at least one string argument")
}
if len(a) > 2 {
return "", errors.New("function takes at most 2 arguments")
}
var ok bool
size := 2
if len(a) > 1 {
if size, ok = a[0].(int); !ok {
return "", errors.New("optional first argument must be an integer")
}
}
text := ""View on GitHub (pinned to dd909d0973)
Solutions
- Read the wrapped error to find the offending type/value; convert map keys to string (or int) before rendering.
- Replace exotic key types with map[string]any or a slice of key/value structs in the data passed to the template.
- Fix or bypass a custom MarshalYAML that returns an error for this value.
- Marshal with yaml.Marshal at the call site (handling the error) instead of using the panicking `yaml` template function.
Example fix
// before (map key is a struct -> encoder error)
data := map[Key]string{...}
tmpl.Execute(w, data) // {{yaml .}}
// after
m := map[string]string{}
for k, v := range data { m[k.String()] = v }
tmpl.Execute(w, m) Defensive patterns
Strategy: try-catch
Validate before calling
if _, err := yaml.Marshal(v); err != nil {
// convert map keys to string or fix MarshalYAML before rendering
} Type guard
func yamlSafeMap(m any) (map[string]any, bool) {
switch t := m.(type) {
case map[string]any:
return t, true
case map[any]any:
out := make(map[string]any, len(t))
for k, v := range t {
ks, ok := k.(string)
if !ok { return nil, false }
out[ks] = v
}
return out, true
}
return nil, false
} Try / catch
defer func() {
if r := recover(); r != nil {
if strings.Contains(fmt.Sprint(r), "failed to marshal as YAML") {
err = fmt.Errorf("template data not YAML-encodable: %v", r)
}
}
}()
b, err = textutil.ExecuteTemplate(tmpl, data) Prevention
- Use string (or int) map keys; avoid struct-typed keys that goccy/go-yaml rejects.
- Test custom MarshalYAML implementations for the values you render.
- Pre-marshal with yaml.Marshal at the call site when data shapes are uncertain.
- Pin/verify goccy/go-yaml behavior when upgrading dependencies.
When it happens
Trigger: Executing a template that calls `{{yaml v}}` where v's type graph cannot be encoded by goccy/go-yaml, such as maps with non-string/int key types the encoder rejects, or values whose MarshalYAML implementation returns an error.
Common situations: Rendering Lima YAML snippets from config objects containing maps keyed by structs or other exotic key types; a custom type with a faulty MarshalYAML used in template data; version upgrades of goccy/go-yaml tightening encoder checks.
Related errors
- failed to marshal as JSON: %+v: %w
- the YAML is invalid, attempted to save the buffer as %#q but
- the YAML is invalid, saved the buffer as %#q: %w
- failed to validate YAML file %#q: %w
- failed to marshal template %#q again after filling defaults:
AI-assisted analysis of lima-vm/lima@dd909d0973 (2026-09-01).
Data as JSON: /api/errors/1f6464e811c25744.
Report an issue: GitHub.