Authoring Docs
Write and organize documentation pages in the Fumadocs docs app, gated by config.docs.
The docs site is apps/docs (a Fumadocs app) gated by config.docs.enabled. It renders Markdown from the repo-root /docs folder (config.docs.contentDir), so the same files appear here and ship into your generated project as AI-agent context (the generated AGENTS.md points coding agents at docs/).
Where content lives
- Pages are
.md/.mdxfiles under/docs. Use.mdxwhen a page needs components; plain.mdworks for prose (JSX renders in both). - Each page sits inside a framework folder (the silo matching your frontend) whose
meta.jsonsets"root": true. - The internal
docs/superpowers/folder (phase plans, specs, audits) is excluded from the build.
Writing style
Pages double as AI-agent context, so density beats prose.
- Structure over sentences: lead with a table,
<Steps>, or bullets; use prose only for the connective why. - Maximize value per word: every line earns its place. Cut filler ("simply", "just", "in order to").
- Be concrete: name the file, key, or command; link a sibling page instead of re-explaining it.
- One idea per heading: short, scannable
##sections, not walls of text. - Clear over clever: plain words, present tense, active voice.
Frontmatter
Validated against Fumadocs' pageSchema. Unlisted keys are silently dropped:
| Field | Required | Description |
|---|---|---|
title | yes | H1 + sidebar label. |
description | recommended | One verb-led sentence; doubles as SEO and the llms.txt blurb. |
icon | no | A Lucide PascalCase name shown in the sidebar. |
full | no | true renders the page full-width (no on-this-page TOC). |
---
title: My Page
description: One verb-led sentence (SEO + llms.txt blurb).
icon: Rocket
---Sidebar order with meta.json
The silo folder's meta.json controls its sidebar. The title labels that silo in the switcher.
{
"title": "My Stack",
"root": true,
"pages": ["index", "---Getting Started---", "quick-start", "..."]
}| Key | Effect |
|---|---|
title | Folder label, shown in the switcher dropdown. |
root: true | Marks the folder a top-level section. Fumadocs builds the switcher from every root folder and isolates the sidebar to the active one. |
pages | Slugs in display order. |
"---Label---" | A pages entry rendered as a section divider. |
"..." | A pages entry that expands to "everything else." |
defaultOpen / collapsible / icon | Optional folder display tweaks (see Fumadocs docs). |
If the boilerplate ships more than one silo, the switcher flips between them with no layout code. A generated project keeps only its own silo.
Components
apps/docs/components/mdx.tsx returns the global component map (getMDXComponents): Fumadocs defaults - <Cards>/<Card>, <Callout> - plus the explicitly added <Steps>/<Step>. Use any of them in any .mdx with no import.
| Component | Use for |
|---|---|
<Cards> / <Card> | Next-step / routing grids. |
<Callout> | A genuine warning or prerequisite. |
<Steps> / <Step> | Ordered setup or checklists. |
Register new MDX components in getMDXComponents, never with a per-file import. Because /docs lives outside apps/docs, a bare import inside a docs page fails the build.
Cross-links
- Link to siblings with a silo-prefixed path:
[Payments](/next/payments). - Never use
/docs/...or a bare/payments. - These links resolve within whichever silo the page is viewed in - that is what lets shared backend pages live identically across silos.
Add a new page
.md / .mdx file under the silo folder in /docs, with title + description frontmatter.pages in the folder's meta.json to place it in the sidebar.pnpm --filter docs dev (default port 3030) to preview.Frequently asked questions
Where do I change which folder gets read?
config.docs.contentDir drives the source directory (this repo reads top-level ../../docs; generated projects default to content/docs). See Configuration.
What's the difference between .md and .mdx?
Both render JSX. Use .mdx by convention when a page relies on components, .md for plain prose; the frontmatter schema is identical.
Why doesn't my page show in the sidebar?
A page only appears once its slug is listed in the silo meta.json pages array - or matched by a "..." catch-all entry.
Customization
Rebrand the boilerplate by editing branding, logo, social, and SEO fields in @repo/config plus your English i18n copy - one source of truth per surface.
Troubleshooting
Fix common development and deployment errors fast, from missing environment variables and background jobs not firing locally to unauthenticated server fetches.