Contents
In brief
MDN shipped a new frontend: unified design on the surface, and under the hood a break from using React as a wrapper around static HTML. The team adopted web components (Lit), custom server components, and a flat component CSS/JS layout so documentation pages do not pay for a full SPA bundle.
What happened
Content still lives in Markdown in git; the build turns it into JSON; the frontend assembles pages on the server. The old stack (yari, ejected Create React App, heavy Webpack, mixed Sass/modern CSS) carried debt: React wrapped docs via dangerouslySetInnerHTML, in-content interactivity used raw DOM APIs, and logic was duplicated.
Since 2024 the team experimented with Lit for embeds (Scrims, interactive examples), then rewrote the site shell: server HTML templating instead of an SPA, isolated custom elements with Declarative Shadow DOM, and per-component CSS/JS instead of one blob per route.
Why it matters
For content-heavy sites (docs, blogs, references), a single React bundle fights reality: most of the page is prose and samples, not an app. React Server Components help but imply framework migration and RSC complexity.
MDN’s approach is closer to islands (Astro-style): cheap static HTML, interactivity only where needed. Web components can be dropped into Markdown macros (<scrim-inline>, <interactive-example>) without reparsing HTML in the client.
| Old yari pain | New direction |
|---|---|
| React cannot “see” Markdown HTML | Web components inside content |
| One CSS bundle for all routes | element.css / server.css per component |
| React + DOM API duplication | One Lit component per widget |
| Extra JS to re-verify static UI | SSR without SPA re-render tax |
In practice
- Avoid SPAs for documentation — local interactivity (copy button, playground, embed) belongs in a custom element or lazy iframe.
- Lit vs React for small state (dialog, lazy iframe) is often simpler: template literals, no JSX build step for an in-article widget.
- Flat component folders (
element.js,server.js,global.css) prevent accidental cross-page style leaks. - Migrate incrementally — MDN rendered Lit inside the legacy React app before rewriting the whole Playground.
If you already use Astro/SSG, you are aligned with this philosophy; the MDN post is a solid reference when arguing against “Next for the entire reference site.”
Takeaway
MDN proves documentation is not an SPA. Web components plus server templating reduce JS, simplify in-content interactivity, and remove the wrapper anti-pattern. Worth revisiting your public docs stack, not only product dashboards.

