Migrate docs to Vocs v2 and Bun#2536
Conversation
|
Cloudflare test deploy is live here: https://codex-jcs-migrate-vocs-v2-bu.celestia-docs-vocs-test.pages.dev/ Latest workflow run after merging Latest immutable deployment URL: Smoke test results from the deployed Pages site:
Notes before switching production to
|
|
🚀 Preview Deployment Your preview is ready: https://celestiaorg.github.io/docs-preview/pr-2536/ |
There was a problem hiding this comment.
Pull request overview
This PR drafts a migration of the Celestia docs site from Next.js/Nextra/Yarn to Vocs v2 on Vite + Bun, updates the build/deploy pipelines accordingly, and introduces a Cloudflare Pages “advanced mode” Worker to serve MCP endpoints on the same origin as the static site.
Changes:
- Replace Next/Nextra app config with Vocs + Vite + Bun, including a generated
src/pagescompatibility layer from the existingapp/**MDX tree. - Add Cloudflare Pages configuration + MCP Worker (served via
_worker.js) and update GitHub Actions workflows for the new build output (out/public). - Rework the Node API OpenRPC docs page rendering/styling and bump the referenced spec to
v0.31.3.
Reviewed changes
Copilot reviewed 42 out of 47 changed files in this pull request and generated 8 comments.
Show a summary per file
| File | Description |
|---|---|
| wrangler.jsonc | Adds Cloudflare Pages project config pointing at out/public. |
| worker/index.js | Adds Pages Worker implementing MCP JSON-RPC tools backed by static markdown assets. |
| vocs.config.ts | Introduces Vocs site config (nav, sidebar, edit links, full-static). |
| vite.config.ts | Adds Vite + Vocs plugin setup and compatibility aliases. |
| tsconfig.json | Removes Next-specific config; adds Vite client + Node types and new excludes. |
| src/vocs/root.css | Adds global CSS (KaTeX + brand fonts + steps styling). |
| src/vocs/layout.tsx | Adds Vocs root layout with JSON-LD and well-known/LLMs link tags. |
| src/vocs/compat/nextra-components.tsx | Provides Vocs-backed replacements for nextra/components (Callout/Tabs/Steps). |
| src/vocs/compat/next-link.tsx | Provides a minimal next/link compatible anchor wrapper. |
| src/vocs/compat/next-image.tsx | Provides a minimal next/image compatible <img> wrapper. |
| src/pages.gen.ts | Adds generated route typing for Waku/Vocs pages. |
| scripts/prepare-vocs-pages.mjs | Generates src/pages from app/** and applies MDX/frontmatter compatibility transforms. |
| scripts/generate-llms.js | Updates OpenRPC spec path/version and writes outputs to out/public when present. |
| scripts/check-links.mjs | Updates script messaging from Nextra to Vocs. |
| README.md | Updates local dev/build/deploy instructions for Bun/Vocs and Cloudflare Pages. |
| plugins/remark-replace-variables.mjs | Updates plugin docstring wording to remove Nextra-specific phrasing. |
| package.json | Replaces Next scripts with Vite/Vocs + Bun workflows and adds new deps (vocs/waku/vite/wrangler). |
| next.config.mjs | Removes Next.js configuration (no longer used). |
| mdx-components.js | Removes Nextra MDX components wiring (no longer used). |
| loaders/strip-mdx-route-metadata.cjs | Removes Nextra-specific MDX loader workaround. |
| eslint.config.mjs | Replaces eslint-config-next with ESLint v9 + typescript-eslint config. |
| components/WrapperWithFooter.tsx | Removes Nextra wrapper component. |
| components/FontStyles.tsx | Removes Next-specific runtime font injection component. |
| components/ContentFooter.tsx | Switches from Next <Link> to <a> and updates accent color variable. |
| components/BaseImage.tsx | Replaces next/image usage with a plain <img> wrapper. |
| app/operate/_page._mdx | Updates Operate landing content/links to new doc paths. |
| app/layout.tsx | Removes Nextra root layout (replaced by Vocs runtime/layout). |
| app/build/rpc/node-api/page.mdx | Updates Node API page MDX (frontmatter + simplified content). |
| app/build/rpc/lib/helper.ts | Tightens classNames typing and removes an eslint disable. |
| app/build/rpc/hooks/useDarkMode.ts | Updates dark-mode detection from Nextra classes to Vocs theme data attribute. |
| app/build/rpc/components/RPCMethod.tsx | Refactors method card markup/classes and removes Nextra styling assumptions. |
| app/build/rpc/components/rpc-api.css | Adds dedicated CSS styling for the RPC docs UI under Vocs. |
| app/build/rpc/components/Playground.tsx | Refactors Headless UI dialog usage (removes Transition wrappers). |
| app/build/rpc/components/ParamModal.tsx | Refactors modal markup/classes to match new CSS system. |
| app/build/rpc/components/NotificationModal.tsx | Makes notification prop optional with a default value. |
| app/build/rpc/components/NodeAPIContent.tsx | Switches to new CSS, new basePath logic, adds v0.31.3, removes dark-mode prop threading. |
| app/build/rpc/components/DynamicRPCTOC.tsx | Removes Nextra-specific TOC DOM-manipulation workaround. |
| app/build/rpc/components/CopyIcon.tsx | Simplifies icon sizing props and removes Nextra classnames. |
| .gitignore | Updates ignores for Vocs/Vite/Bun outputs and Cloudflare artifacts. |
| .github/workflows/README.md | Updates workflow documentation for Bun/Vocs and adds Cloudflare deploy notes. |
| .github/workflows/preview.yaml | Updates PR preview build to Bun and publishes out/public. |
| .github/workflows/lint.yaml | Updates lint/link-check jobs to Bun install/run. |
| .github/workflows/deploy.yml | Updates GitHub Pages deploy to Bun and publishes out/public. |
| .github/workflows/deploy-cloudflare.yml | Adds optional Cloudflare Pages deploy workflow for migration testing. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
| @@ -58,7 +54,7 @@ jobs: | |||
| rm -rrf "$TARGET_DIR"/* | |||
| const pages = await getPages(env) | ||
| const contents = await Promise.all( | ||
| pages.map(async (pagePath) => ({ | ||
| pagePath, | ||
| text: await readPageMarkdown(env, pagePath), | ||
| })), | ||
| ) |
| const url = new URL(request.url) | ||
| const isMcpPath = url.pathname === '/mcp' || url.pathname === '/api/mcp' | ||
|
|
| useEffect(() => { | ||
| const observer = new MutationObserver(() => { | ||
| setIsDark(document.documentElement.classList.contains('dark')); | ||
| setIsDark(readIsDark()); | ||
| }); | ||
|
|
||
| observer.observe(document.documentElement, { | ||
| attributes: true, | ||
| attributeFilter: ['class'] | ||
| attributeFilter: ['data-vocs-theme', 'style'] | ||
| }); | ||
|
|
||
| return () => observer.disconnect(); | ||
| }, []); |
| <div className='rpc-param-modal' aria-labelledby='modal-title' role='dialog' aria-modal='true'> | ||
| <div className='rpc-param-modal__panel'> |
| async function copyAppTree(currentDir = appDir) { | ||
| const entries = await readdir(currentDir, { withFileTypes: true }) | ||
|
|
||
| for (const entry of entries) { | ||
| const sourcePath = path.join(currentDir, entry.name) | ||
| const relativePath = path.relative(appDir, sourcePath) | ||
|
|
||
| if (entry.isDirectory()) { | ||
| await copyAppTree(sourcePath) | ||
| continue | ||
| } | ||
|
|
||
| if (!entry.isFile() || ignoredFiles.has(entry.name)) continue | ||
|
|
||
| let targetRelativePath = relativePath | ||
| if (entry.name === 'page.mdx' || entry.name === '_page._mdx') { | ||
| targetRelativePath = path.join(path.dirname(relativePath), 'index.mdx') | ||
| } | ||
|
|
||
| const targetPath = path.join(generatedPagesDir, targetRelativePath) | ||
| await mkdir(path.dirname(targetPath), { recursive: true }) | ||
| generatedFiles.add(toPosix(path.relative(generatedPagesDir, targetPath))) | ||
|
|
||
| if (entry.name.endsWith('.mdx')) { | ||
| const content = await readFile(sourcePath, 'utf8') | ||
| await writeFile(targetPath, withVocsMdxCompatibility(content)) | ||
| } else { | ||
| await cp(sourcePath, targetPath) | ||
| } |
| '> Official documentation for Celestia, the modular blockchain powering unstoppable apps with full-stack control.', | ||
| '', | ||
| 'These docs are built with Next.js + Nextra and exported statically. Links below point to canonical markdown pages so tools and LLMs can ingest clean text.', | ||
| 'These docs are built with Vocs and exported statically. Links below point to canonical markdown pages so tools and LLMs can ingest clean text.', |
Summary
Draft migration of the Celestia docs from Next/Nextra/Yarn to Vocs v2, Vite, and Bun.
This also adds the Eden-style Cloudflare Pages setup: the docs build remains full-static, and
worker/index.jsis copied intoout/public/_worker.jsto serve/mcpand/api/mcpon the same origin.What changed
src/pagescompatibility from the existingapp/**/page.mdxtree.out/publicoutput.wrangler.jsonc.v0.31.3.Validation
bun install --frozen-lockfilebun run lintbun run prepare:cloudflare/api/mcpinitialize=>200/api/mcpnotifications/initialized=>202/api/mcpread_pagefor/build/rpc/node-apireturns# Node APINotes
This is draft while we verify the migrated docs surface and decide how to cut over production from the current GitHub Pages deployment to Cloudflare Pages.