Skip to content

Move the reference out of the README and into a docs site - #1

Merged
CodyEngel merged 2 commits into
mainfrom
claude/astro-starlight-docs-site-64gaca
Aug 12, 2026
Merged

Move the reference out of the README and into a docs site#1
CodyEngel merged 2 commits into
mainfrom
claude/astro-starlight-docs-site-64gaca

Conversation

@CodyEngel

@CodyEngel CodyEngel commented Aug 12, 2026

Copy link
Copy Markdown
Owner

Astro + Starlight in site/, published to https://morse-ai.com by Cloudflare Workers Builds.

What is here

The site — 15 pages under site/src/content/docs/, split the way someone arrives at them rather than as one scroll:

Group Pages
index.mdx (splash: tagline, room diagram, three cards)
Getting started Quick start · Rooms
Concepts Why agents block instead of listening · Knowing when it is over · Discovery is a capability directory · What being in the room costs
Guides Role files · Agent folders other tools keep · Other harnesses
Reference MCP tools · CLI · Environment · Packages
Security and data · a custom 404

The sidebar is explicit in astro.config.mjs, not autogenerated. Every page is derived from README.md, SECURITY.md, or the source — no invented behaviour.

The README is trimmed to banner, description, diagram, quick start, the security warning, and links. Detail moved rather than being duplicated, so there is one place to fix a wrong sentence.

Keeping it that way is the part that needed machinery, since drift stops being visible in review once the detail leaves the README:

  • AGENTS.md maps each documented surface to the page that describes it; CLAUDE.md points at it so every harness reads the same rules.
  • .github/workflows/docs.yml has a sync job that fails a PR touching a documented surface (CLI, MCP tools, env vars, role/plugin contract, SECURITY.md) without touching site/src/content/docs/. Escape hatch: docs: n/a in the PR body.
  • npm run build in site/ also checks every internal link — anchors included — against what was actually emitted (site/scripts/check-links.mjs).

Deploys belong to Cloudflare, not to CI. wrangler.jsonc at the root, assets-only, serving ./site/dist — the same shape engel.dev uses. Workers Builds clones on push, runs the build command, then npx wrangler deploy, so there is no API token in this repository. The workflow keeps only the half Cloudflare cannot do: failing a pull request before it merges.

Dashboard settings, also recorded in CONTRIBUTING.md and wrangler.jsonc since they are invisible from the repo:

Setting Value
Build command npm run docs:build
Deploy command npx wrangler deploy (default)
Non-production branch deploy npx wrangler versions upload (default)
Root directory / (default)

Isolation: site/ is a standalone npm project, deliberately outside the workspace packages/* glob and marked "private": true. npm ci at the root installs no Astro, and a docs dependency has no route into a published package. Only astro and @astrojs/starlight. Nothing under packages/, test/, scripts/ or docs/plans/ was touched.

Verified

  • npm run docs:build — 16 pages, 357 internal links, all resolve
  • npm ci + npm run build inside site/ (what CI does) — green
  • npm test — 138 pass, unchanged

Things worth your feedback

  1. Only one dashboard field differs from the defaults, and it is load-bearing: the build command must be npm run docs:build, not npm run build — at the workspace root that means tsc over the three packages and produces no site. Two optional settings are worth adding too, both in CONTRIBUTING.md: build watch paths (site/*, wrangler.jsonc) so a code-only commit does not rebuild the site, and SKIP_DEPENDENCY_INSTALL=1 so the build image does not install the root workspace and run tsc for a docs deploy that does not need it.

  2. The Worker name is morse, matching the project name in your setup screenshot. If you would rather call it morse-docs, change both — a mismatch is silent, wrangler deploys the name in wrangler.jsonc and leaves the connected Worker untouched.

  3. morse-ai.com still has to be attached to the Worker in the dashboard. wrangler.jsonc deliberately declares no routes, so a deploy cannot fail on a zone the config cannot see; until the domain is attached it serves on workers.dev.

  4. The scaffold command could not run here. This sandbox's egress policy blocks codeload.github.com (403), and npm create astro@latest -- --template starlight fetches the template from GitHub. So I built the same files by hand against the published packages (astro@7.2.1, @astrojs/starlight@0.41.7): astro.config.mjs, src/content.config.ts with docsLoader/docsSchema, a tsconfig.json extending astro/tsconfigs/strict, public/favicon.svg, .gitignore. It builds clean, but if you want it byte-identical to the official template, re-running the scaffold locally and diffing is the check I could not do.

  5. Two small additions beyond the spec you gave me, both easy to revert: not_found_handling: "404-page" in wrangler.jsonc plus a real 404 page, so an unknown URL gets the site's own 404; and the root docs:* scripts run npm --prefix site install before the underlying command, so npm run docs:build works from a fresh clone instead of failing with astro: not found.

  6. The sync guard is opinionated and will affect contributors, not just agents. The surface list is a regex in docs.yml — I scoped it to what a docs reader would notice (cli/main.ts, cli/agent.ts, the three mcp.ts files, prompt.ts, roles.ts, plugins.ts, toml.ts, README.md, SECURITY.md). If it turns out noisy, narrowing that regex is a one-line change. Tell me if you would rather it warned than failed.

  7. No <!-- TODO --> markers survived. The one place the README left a schema unstated — the plugin manifest fields — I filled in from packages/registry/src/plugins.ts (id, project, personal, depth, extensions, format, map) rather than guessing or leaving a hole. Same for the rejection reason strings (outside the searched directory / unreadable / unparseable) and the thread-id example format. Worth a skim on guides/agent-folders.md in particular.

  8. Small README fix carried along: the old quick start said "In a seventh terminal" after a three-agent example — a leftover from the six-agent version. The site says "In another terminal".

  9. The splash has no hero image. assets/social/morse-linkedin.png exists, but using it would mean copying a binary into site/; I left the hero text-only. Easy to add if you want it. The favicon is a plain dot-dash SVG I drew — swap it if there is real brand art.

🤖 Generated with Claude Code

https://claude.ai/code/session_01V8CHi3o1YanuKYvQzS1giK

claude added 2 commits August 12, 2026 05:43
The README had become the whole manual: 350 lines covering the design,
the role contract, plugin manifests, both CLI surfaces, the environment,
and the package split. That reads as one linear scroll, and every one of
those sections wants to stand alone.

site/ is Astro + Starlight, published to https://morse-ai.com as an
assets-only Cloudflare Worker. Fifteen pages, split the way someone
arrives at them: getting started, then why it works this way, then how
to configure it, then reference. Nothing is invented — every page is
derived from the README, SECURITY.md, or the source, and the two places
the README left a schema unstated (plugin manifest fields) are filled in
from packages/registry/src/plugins.ts rather than guessed.

The README keeps the banner, the description, the diagram, the quick
start, the security warning, and links. Detail moved rather than being
duplicated, so there is one place to fix a wrong sentence.

Keeping it that way is the part that needs machinery:

- AGENTS.md maps each documented surface to the page that describes it,
  and CLAUDE.md points at it, so every harness reads the same rules
- .github/workflows/docs.yml fails a pull request that changes one of
  those surfaces without touching site/src/content/docs/. "docs: n/a"
  in the PR body is the escape hatch when a change genuinely is not
  described anywhere
- npm run build in site/ also checks every internal link, anchors
  included, against what was actually emitted

site/ is a standalone npm project, deliberately outside the workspace
packages/* glob: npm ci at the root installs no Astro, and a docs
dependency has no route into a published package. Its only dependencies
are astro and @astrojs/starlight. Root scripts docs:dev, docs:build and
docs:deploy install it on demand, so a fresh clone needs no extra step.

Deploys run from main on a push touching site/ or wrangler.jsonc, using
a CLOUDFLARE_API_TOKEN secret. The custom domain is attached in the
dashboard rather than declared in wrangler.jsonc, so a deploy cannot
fail on a zone the config cannot see.

npm test is unchanged and green at 138.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01V8CHi3o1YanuKYvQzS1giK
The git integration does what the workflow was doing, and does it with a
token this repository never has to hold: Cloudflare clones on push, runs
the build command, then `wrangler deploy` — the same shape engel.dev
already uses, wrangler config at the root with assets pointing into the
subdirectory that builds them.

- docs.yml keeps the half Cloudflare cannot do — build and link-check a
  pull request before it merges — and deploys nothing. The comment says
  why, so the next person does not helpfully add it back and race the
  integration for the same Worker.
- No CLOUDFLARE_API_TOKEN secret. Workers Builds mints its own.
- The Worker is named `morse`, matching the project the repository is
  connected to. A mismatch here is silent: wrangler deploys the name in
  the file and leaves the connected Worker alone.
- CONTRIBUTING.md records the dashboard settings, since they are
  invisible from the repository. Only the build command differs from the
  defaults: `npm run docs:build`, not `npm run build`, which at the
  workspace root is tsc over the three packages and produces no site.

`npm run docs:deploy` stays as break-glass from a laptop.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01V8CHi3o1YanuKYvQzS1giK

Copy link
Copy Markdown
Owner Author

Switched deployment to Cloudflare Workers Builds (0c9e712), same shape engel.dev uses — wrangler config at the repo root with assets pointing into the subdirectory that builds them.

In the dialog you screenshotted, change one field:

Field Value
Project name morse — matches "name" in wrangler.jsonc now
Build command npm run docs:build ← not npm run build
Deploy command npx wrangler deploy (leave as-is)
Builds for non-production branches leave checked — gives PRs a preview URL via wrangler versions upload

npm run build at the workspace root is tsc over the three packages; it produces no site, so the deploy would upload an empty site/dist. docs:build installs site/'s dependencies, builds Astro, and checks every internal link before wrangler ever runs.

Under Advanced settings, two things worth setting (both documented in CONTRIBUTING.md, neither required):

  • Build watch paths → include site/* and wrangler.jsonc. A commit that only touches packages/ cannot change the site, so it should not rebuild it.
  • Build variable SKIP_DEPENDENCY_INSTALL=1. Otherwise the build image installs the root workspace, which runs preparetsc over all three packages before the docs build starts. docs:build installs what it actually needs on its own.

The build image defaults to Node 24, which clears both this repo's 22.13 floor and Astro's.

What changed in the repo: .github/workflows/docs.yml no longer deploys — no CLOUDFLARE_API_TOKEN secret needed anywhere. It keeps the part Cloudflare cannot do: building and link-checking a pull request before it merges, plus the docs-sync guard. The workflow comment says why there is no deploy step, so it does not get helpfully added back and race the git integration for the same Worker. npm run docs:deploy stays as break-glass from a laptop.

Still outstanding on your side: attaching morse-ai.com to the Worker. wrangler.jsonc declares no routes on purpose, so the first deploy cannot fail on a zone it cannot see — it will serve on workers.dev until the custom domain is added.


Generated by Claude Code

@CodyEngel
CodyEngel merged commit 426a8a0 into main Aug 12, 2026
9 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants