gohugoio/hugo · critical
unknown shortcode token %q (number of tokens: %d)
Error message
unknown shortcode token %q (number of tokens: %d)
What it means
A panic raised by the token handler in page__content.go's content-rendering path when, after markdown processing, Hugo finds a HUGOSHORTCODE-style placeholder token in the output that has no matching entry in ct.contentPlaceholders. The code comments this as "should never happen" — it indicates internal state corruption: a placeholder survived into rendered content without a registered renderer.
Source
Thrown at hugolib/page__content.go:562
}
// There are one or more replacement tokens to be replaced.
var hasShortcodeVariants bool
tokenHandler := func(ctx context.Context, token string) ([]byte, error) {
if token == tocShortcodePlaceholder {
return []byte(ct.tableOfContentsHTML), nil
}
renderer, found := ct.contentPlaceholders[token]
if found {
repl, more, err := renderer.renderShortcode(ctx)
if err != nil {
return nil, err
}
hasShortcodeVariants = hasShortcodeVariants || more
return repl, nil
}
// This should never happen.
panic(fmt.Errorf("unknown shortcode token %q (number of tokens: %d)", token, len(ct.contentPlaceholders)))
}
b, err = expandShortcodeTokens(ctx, b, tokenHandler)
if err != nil {
return nil, err
}
if hasShortcodeVariants {
cp.po.p.incrPageOutputTemplateVariation()
}
var result contentSummary
if c.pi.hasSummaryDivider {
s := string(b)
summarized := page.ExtractSummaryFromHTMLWithDivider(cp.po.p.m.pageConfigSource.ContentMediaType, s, internalSummaryDividerBase)
result.summary = page.Summary{
Text: template.HTML(summarized.Summary()),
Type: page.SummaryTypeManual,
Truncated: summarized.Truncated(),View on GitHub ↗ (pinned to 8a468df065)
Solutions
- Restart `hugo server` (or run `hugo --gc` and clear resources/_gen and the cacheDir) to rule out stale cached content state.
- Search content and layouts for anything emitting the literal internal placeholder pattern (e.g. `grep -r HAHAHUGOSHORTCODE content layouts`) and remove it.
- Check whether a render hook or shortcode copies raw page source (.RawContent) into output — that duplicates placeholders; use .Content or rework the hook.
- If reproducible on a clean build, minimize the site and report it as a bug at github.com/gohugoio/hugo — this path is an internal invariant violation (it panics).
Defensive patterns
Strategy: validation
Validate before calling
// don't manipulate rendered content in ways that split/drop shortcode placeholder tokens // e.g. avoid truncating .Content or regex-replacing over raw placeholder markers before rendering completes
Try / catch
if _, err := p.Content(ctx); err != nil && strings.Contains(err.Error(), "unknown shortcode token") {
// internal token mismatch — usually a content-mangling markup hook or truncation
return err
} Prevention
- Do not post-process markdown output with hooks that strip or rewrite unknown HTML comments (placeholders live there)
- Use .Summary/.Truncated APIs instead of hand-slicing rendered content
- Report reproducers upstream — this is an internal invariant violation, not normal user error
When it happens
Trigger: expandShortcodeTokens encounters a placeholder string in Goldmark output that isn't in the placeholder map. In practice: content or a markdown render hook that synthesizes/duplicates text containing a raw `HAHAHUGOSHORTCODE` placeholder, or a Hugo bug where placeholder bookkeeping diverges between parse and render (e.g. cached content reused across edits in `hugo server`).
Common situations: Render hooks or shortcodes that echo page content verbatim (duplicating placeholder tokens); pathological content literally containing the internal placeholder marker; stale-cache states in long-running `hugo server` sessions after rapid edits; rarely, genuine regressions in a new Hugo release.
Related errors
- failed to render shortcode %q: %w
- illegal state in content; shortcode token missing end delim
- failed to render shortcode: %w
- RenderString: unknown shortcode token %q
- max depth exceeded
AI-assisted analysis of gohugoio/hugo@8a468df065 (2026-07-31).
Data as JSON: /data/errors/b6fd223fc10ad206.json.
Report an issue: GitHub ↗.