thanos-io/thanos · error
failed to parse template
Error message
failed to parse template
What it means
In Thanos's rule UI URL templating (thanos rule, --alert.query-template style), the user-provided Go text/template used to build links like "/graph?g0.expr={{.Expr}}" is parsed with text/template. If the template string is not syntactically valid Go template syntax, errors.Wrap produces "failed to parse template" and URL generation aborts. The template is executed with an Expression struct exposing only the .Expr field (URL-query-escaped PromQL).
Solutions
- Check the template string for balanced, valid Go template actions: every {{ must have a matching }} and valid syntax (see https://pkg.go.dev/text/template).
- Only reference fields that exist on the Expression data: use {{.Expr}} (the URL-escaped PromQL expression); other fields will fail at execute time, but syntax errors surface here.
- Test the template offline with template.New("test").Parse(tmpl) in a scratch Go program or rely thanos's own validateTemplate path before deploying.
- If the flag comes from a YAML/Env config, verify shell/JSON escaping did not swallow or duplicate braces.
Example fix
// before
tmpl := "/graph?g0.expr={{{.Expr}}}&g0.tab=1"
// after
tmpl := "/graph?g0.expr={{.Expr}}&g0.tab=1" Defensive patterns
Strategy: validation
Validate before calling
func validTemplate(s string) bool {
_, err := texttemplate.New("check").Parse(s)
return err == nil
}
// require validTemplate(tmpl) before passing to thanos rule flags Type guard
null
Try / catch
if _, err := texttemplate.New("url").Parse(tmpl); err != nil {
return fmt.Errorf("invalid url template %q: %w", tmpl, err)
} Prevention
- Keep templates to the minimal form "/graph?g0.expr={{.Expr}}&g0.tab=1" unless you have a tested reason otherwise
- Run template validation (thanos's validateTemplate) in CI for any config that embeds Go templates
- Beware of shell/YAML brace escaping when passing templates via flags or manifests
When it happens
Trigger: Calling the URL-template function (invoked when generating external query links for alerts/rules) with a tmpl string containing malformed Go template syntax, e.g. unbalanced {{ }} braces, an unclosed action, or invalid pipeline syntax, causing texttemplate.New("url").Parse(tmpl) to fail.
Common situations: Operators hand-write the URL template flag and typo the delimiters (e.g. "/graph?g0.expr={{{.Expr}}}" or a stray {{without an end}}); copying a Jinja2/Handlebars-style template instead of Go syntax; quoting issues in YAML/CLI mangle the braces.
Understand the failure class
- Parsing and encoding errors: unexpected token, malformed input — why parsers reject input and how to find the real culprit.
Related errors
- failed to execute template
- invalid alert source template
- failed to parse the template
- failed to execute the template
- error while parsing config for request logging
AI-assisted analysis of thanos-io/thanos@35b8b99117 (2026-09-07).
Data as JSON: /api/errors/e3c107e772bb0992.
Report an issue: GitHub.
Appendix: source
Thrown at cmd/thanos/rule.go:1130
metrics.configSuccess.Set(1)
metrics.configSuccessTime.Set(float64(time.Now().UnixNano()) / 1e9)
metrics.rulesLoaded.Reset()
for _, group := range ruleMgr.RuleGroups() {
metrics.rulesLoaded.WithLabelValues(group.PartialResponseStrategy.String(), group.OriginalFile, group.Name()).Set(float64(len(group.Rules())))
}
return errs.Err()
}
func tableLinkForExpression(tmpl string, expr string) (string, error) {
// template example: "/graph?g0.expr={{.Expr}}&g0.tab=1"
escapedExpression := url.QueryEscape(expr)
escapedExpr := Expression{Expr: escapedExpression}
t, err := texttemplate.New("url").Parse(tmpl)
if err != nil {
return "", errors.Wrap(err, "failed to parse template")
}
var buf bytes.Buffer
if err := t.Execute(&buf, escapedExpr); err != nil {
return "", errors.Wrap(err, "failed to execute template")
}
return buf.String(), nil
}
func validateTemplate(tmplStr string) error {
tmpl, err := template.New("test").Parse(tmplStr)
if err != nil {
return fmt.Errorf("failed to parse the template: %w", err)
}
var buf bytes.Buffer
err = tmpl.Execute(&buf, Expression{Expr: "test_expr"})
if err != nil {
return fmt.Errorf("failed to execute the template: %w", err)View on GitHub (pinned to 35b8b99117)