gohugoio/hugo · error
RenderString: unknown shortcode token %q
Error message
RenderString: unknown shortcode token %q
What it means
The RenderString-path analog of the placeholder-lookup failure: when RenderString renders text containing shortcodes, each shortcode is replaced by a placeholder token and later expanded; if a token in the rendered output has no matching renderer in the placeholder map (and isn't the TOC placeholder), this error is returned. The code marks it "should not happen" — an internal bookkeeping invariant broke, though unlike the page-content path it returns an error instead of panicking.
Source
Thrown at hugolib/page__content.go:1005
if token == tocShortcodePlaceholder {
toc, err := c.contentToC(ctx)
if err != nil {
return nil, err
}
// The Page's TableOfContents was accessed in a shortcode.
return []byte(toc.tableOfContentsHTML), nil
}
renderer, found := placeholders[token]
if found {
repl, more, err := renderer.renderShortcode(ctx)
if err != nil {
return nil, err
}
hasShortcodeVariants = hasShortcodeVariants || more
return repl, nil
}
// This should not happen.
return nil, fmt.Errorf("RenderString: unknown shortcode token %q", token)
}
rendered, err = expandShortcodeTokens(ctx, rendered, tokenHandler)
if err != nil {
return "", err
}
if hasShortcodeVariants {
pco.po.p.incrPageOutputTemplateVariation()
}
}
// We need a consolidated view in $page.HasShortcode
combined := pco.po.p.m.content.hasShortcode.Load().Or(parseInfo.shortcodeParseInfo.hasName)
pco.po.p.m.content.hasShortcode.Store(&combined)
} else {
si := sourceInfo{
filename: pco.po.p.pathOrTitle() + " (rendered from string)",View on GitHub ↗ (pinned to 8a468df065)
Solutions
- Check the string you pass to RenderString for a literal internal placeholder pattern (HAHAHUGOSHORTCODE...) — strip or avoid feeding pipeline output back in; render from the raw source instead.
- Restart `hugo server` / clear caches to eliminate stale placeholder state.
- Reduce to a minimal reproduction; if it reproduces on a clean build with plain input, file a bug at github.com/gohugoio/hugo including the input string and shortcodes involved.
Defensive patterns
Strategy: validation
Validate before calling
{{/* ensure any shortcode named inside the RenderString input exists in layouts/_shortcodes/ */}}
{{ $out := .RenderString "{{</* myshortcode */>}}" }} Try / catch
if err := h.Build(cfg); err != nil && strings.Contains(err.Error(), "RenderString: unknown shortcode token") {
// shortcode used in RenderString input isn't resolvable in that context
return err
} Prevention
- Verify shortcodes referenced in RenderString input exist and are spelled correctly
- Avoid shortcodes that depend on page context when rendering detached strings
- Cover RenderString-with-shortcode paths in hugolib.Test integration tests
When it happens
Trigger: Calling `.RenderString` on a string containing `{{< shortcode >}}` markup where the token map built during parsing doesn't cover a token found post-render — e.g. input text that literally contains a Hugo placeholder marker, or the rendered markdown mangling/duplicating a token so it no longer matches.
Common situations: Passing content that already went through Hugo's pipeline (containing leftover placeholder strings) into RenderString; markdown processing that splits a placeholder across elements in unusual markup configurations; genuine Hugo regressions after upgrades.
Related errors
- unknown shortcode token %q (number of tokens: %d)
- invalid Highlight option: %s
- failed to render shortcode %q: %w
- no earlier definition of shortcode %q found
- shortcode has no name
AI-assisted analysis of gohugoio/hugo@8a468df065 (2026-07-31).
Data as JSON: /data/errors/d6b90d78be93b8a5.json.
Report an issue: GitHub ↗.