Internal links written in Markdown post content are not rewritten to the current locale. A raw link like /posts/2025/12/15/... or /support-care on a German
(*.de.md) post resolves to the English default locale. If the target only exists in German (e.g. a *.de.md-only post), this produces a 404.
Concrete example that broke on a deploy preview:
- Written in a
.de.md post: /posts/2025/12/15/cyber-resilience-act-übersicht-und-auswirkungen
- Result:
…/posts/2025/12/15/… → 404
- Correct target:
…/de/posts/2025/12/15/…
Current workaround: authors must hard-code the /de prefix in every internal link inside German posts. This is error-prone and easy to forget, and it couples content to the
routing scheme.
Goal
Internal links in Markdown content should automatically resolve to the locale of the post being rendered. Authors write locale-neutral links (e.g. /posts/2025/12/15/...,
/support-care) and the renderer prefixes the active locale where needed.
Where
The Markdown pipeline already post-processes <a> tags in src/lib/markdown.ts:
isExternalContentLink() — distinguishes external vs. internal hrefs
addExternalLinkIcon() + the <a …href=…> regex (~line 372) — currently only appends an external-link icon
- The render entry point (
remark().use(remarkGfm).use(html, { sanitize: false })…, ~line 712) needs access to the current locale so it can rewrite internal hrefs.
Tasks
Acceptance criteria
- A locale-neutral internal link in a
*.de.md post renders with the /de prefix and resolves without a 404.
- The same link in an English post renders without a prefix.
- External links, anchors, and assets are unchanged; no double locale prefixes.
References
src/lib/markdown.ts — isExternalContentLink(), addExternalLinkIcon(), <a> post-processing regex (~line 372), render entry (~line 712)
src/components/blog/BlogCard.tsx, src/lib/rss.ts — existing localePath logic (locale === 'en' ? '' : '/${locale}')
Internal links written in Markdown post content are not rewritten to the current locale. A raw link like
/posts/2025/12/15/...or/support-careon a German(
*.de.md) post resolves to the English default locale. If the target only exists in German (e.g. a*.de.md-only post), this produces a 404.Concrete example that broke on a deploy preview:
.de.mdpost:/posts/2025/12/15/cyber-resilience-act-übersicht-und-auswirkungen…/posts/2025/12/15/…→ 404…/de/posts/2025/12/15/…Current workaround: authors must hard-code the
/deprefix in every internal link inside German posts. This is error-prone and easy to forget, and it couples content to therouting scheme.
Goal
Internal links in Markdown content should automatically resolve to the locale of the post being rendered. Authors write locale-neutral links (e.g.
/posts/2025/12/15/...,/support-care) and the renderer prefixes the active locale where needed.Where
The Markdown pipeline already post-processes
<a>tags insrc/lib/markdown.ts:isExternalContentLink()— distinguishes external vs. internal hrefsaddExternalLinkIcon()+ the<a …href=…>regex (~line 372) — currently only appends an external-link iconremark().use(remarkGfm).use(html, { sanitize: false })…, ~line 712) needs access to the current locale so it can rewrite internal hrefs.Tasks
isExternalContentLink()) and not already locale-prefixed, prepend thelocale path (
en→ no prefix,de→/de) — mirroring thelocalePathlogic used inBlogCard.tsx/rss.ts.#…),mailto:/tel:and asset paths untouched./de/...links in content can be simplified back to locale-neutral form (optional cleanup).Acceptance criteria
*.de.mdpost renders with the/deprefix and resolves without a 404.References
src/lib/markdown.ts—isExternalContentLink(),addExternalLinkIcon(),<a>post-processing regex (~line 372), render entry (~line 712)src/components/blog/BlogCard.tsx,src/lib/rss.ts— existinglocalePathlogic (locale === 'en' ? '' : '/${locale}')