Skip to content

Refresh site metadata, add structured data, llms.txt, and a Copy page menu - #39

Merged
samkim merged 7 commits into
mainfrom
site-metadata
Oct 23, 2026
Merged

samkim merged 7 commits into
mainfrom
site-metadata

Conversation

@samkim

@samkim samkim commented Oct 23, 2026 •

Copy link
Copy Markdown
Member

Summary

The site's metadata had fallen behind the landing-page redesign (#31), and the generated reference pages had broken descriptions. This brings both up to date, adds structured data and per-page share cards, and makes the docs easy for agents and LLM tools to read, including a Copy page menu on every docs page.

Out-of-date metadata, fixed

  • Site description and landing title now match the redesigned hero.
  • All 30 CRD reference pages had descriptions cut off mid-sentence ("…defined by: model, system"). The generator took the first line of a wrapped Go doc comment; mdxutil.Summary now takes the first full sentence, capped at snippet length.
  • CLI reference descriptions were bare cobra fragments ("Manage AgentClass resources"). They now name the command and what the page holds.
  • Regenerating also brought the AgentSession reference up to date: it was missing the per-pod cost fields and costTreatment already in the CRDs.

SEO

  • JSON-LD: Organization, WebSite and SoftwareSourceCode on every page; TechArticle and a Home › Docs › page BreadcrumbList on each guide. Every @id a page references is defined on that page (tested).
  • A share card per guide (section, title, summary) instead of one site-wide card. Twitter inherits it.
  • article:section, author/publisher, and googleBot max-snippet/max-image-preview directives.
  • Descriptions are stripped of Markdown before they reach meta tags.
  • The 404 page had a noindex beside the layout's index, follow; it now carries one consistent directive.
  • pnpm check fails any guide without a description.
  • The sitemap and robots.txt already existed and were correct; they're unchanged.

Agent access

  • Every guide as Markdown at /docs/<slug>.md, and at /docs/<slug> for requests sending Accept: text/markdown. These are noindex with a Link: rel=canonical to the HTML page.
  • /llms.txt (index by section, per llmstxt.org) and /llms-full.txt (every guide in one file).
  • <link rel="alternate" type="text/markdown"> on each guide, and an llms.txt link in the footer.
  • The MDX-to-Markdown transform (site/lib/markdown.ts) is tested against all 136 guides and fails if one uses a component the transform doesn't translate.

Copy page menu

A split button beside each guide's title, modeled on the one in the AuthZed docs:

  • Copy page: copies the page as Markdown ("Copied" / "Copy failed" feedback).
  • View as Markdown: opens the plain-text version.
  • Open in ChatGPT / Open in Claude: a new chat prefilled with "Read from https://openap.org/docs/&lt;page&gt;.md so I can ask questions about it."

Keyboard: focus moves into the menu on open, arrow keys move between items and wrap, Escape closes and returns focus. The Markdown is fetched inside the clipboard write (a ClipboardItem promise) because Safari drops a click's clipboard permission across an await.

Screenshots

Copy page menu (dark / light)

After copying, and at phone width

Per-page share cards (previously every page used the site-wide card)

/llms.txt and a page's Markdown (/docs/plan-gating.md)

The screenshots were committed and removed in the next commit, so they're linked by commit SHA and the net diff contains none. Squash-merging keeps them out of main.

Testing

Site gate (all passed): pnpm check, pnpm lint, pnpm typecheck, pnpm test (259 tests), pnpm build (136 pages prerendered and indexed).

Generators: go build ./..., go vet ./pkg/gen/..., go test ./pkg/gen/... passed; new tests for mdxutil.Summary and the CLI family description.

Against a production build (pnpm start):

  • Every doc page's head checked: description, canonical, markdown alternate, OG/Twitter tags with the per-page image, and the JSON-LD graph (parsed).
  • /docs/<slug>.md → 200 text/markdown, X-Robots-Tag: noindex, canonical Link; Accept: text/markdown on /docs/<slug> → Markdown, a browser Accept → HTML; unknown slug .md → 404.
  • /llms.txt lists all 136 guides; /llms-full.txt contains all 136.
  • Copy page in Chrome against the real system clipboard: put a sentinel on the macOS clipboard, clicked the button, and pbpaste matched /docs/plan-gating.md byte for byte (3,848 bytes). Menu keyboard behavior, link targets, the "Copied" reset and the failure state were checked in the browser.

Repo ship gate:

  • mage test:unit: ✅ passed
  • mage test:integration: ⏳ running
  • mage test:e2e: ⏳ queued

This PR is a draft until all three finish. The Go changes are limited to pkg/gen (docs generators).

Not covered / follow-ups

  • Safari: Copy page hasn't been tested there.
  • Share-image alt text is the same on every doc card. Next 16 passes generateImageMetadata no params under a dynamic segment at build time, so it can't name the page. The images themselves are per page.
  • Vary: Accept: locally, Next's own Vary replaced the configured one on the HTML response. It should be checked on a Vercel preview. Vercel evaluates the Accept rewrite before its cache either way.
  • The ChatGPT and Claude menu items use a generic chat icon, not the brand logos.

🤖 Generated with Claude Code

samkim and others added 5 commits October 23, 2026 13:22
The CRD reference pages took their meta description from the first line
of a Go doc comment, which wraps at ~80 columns, so every description
stopped mid-sentence ("...defined by: model, system"). mdxutil.Summary
takes the first full sentence instead, capped at a search snippet's
length. CLI family pages now name the command and what the page holds
rather than repeating cobra's bare Short.

Regenerating also brings the AgentSession reference up to date with the
per-pod cost fields and costTreatment, which had drifted from the CRDs.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
- Site description and landing title match the redesigned hero.
- JSON-LD: Organization, WebSite and SoftwareSourceCode on every page,
  plus TechArticle and BreadcrumbList on each guide.
- A share card per guide (section, title, summary) instead of the one
  site-wide card.
- Every guide as Markdown at /docs/<slug>.md, or /docs/<slug> with
  Accept: text/markdown; /llms.txt indexes them and /llms-full.txt is
  the whole set. Text responses are noindex with a canonical Link.
- pnpm check fails a guide without a description; the 404 page carries
  one noindex instead of a contradicting pair.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
A split button beside each guide's title copies the page as Markdown.
Its menu also views the Markdown or opens ChatGPT or Claude with a
prompt to read it. The chat links hand over the .md rendition so the
model reads the guide without the site chrome.

The Markdown is fetched inside the clipboard write (a ClipboardItem
promise), since Safari drops the click's clipboard permission across
an await. README and AGENTS.md describe the agent-facing features.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@vercel

vercel Bot commented Oct 23, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
openagentprimitives Ready Ready Preview Oct 23, 2026 9:41pm UTC

Request Review

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@samkim
samkim marked this pull request as ready for review October 23, 2026 21:25
- The per-guide OG image route sets dynamicParams = false like its
  siblings, so an unknown slug is a 404 rather than a 500.
- guideSource checks the slug names a guide before turning it into a
  file path, instead of relying on every caller to have checked.
- mdxutil.Summary backs a space-free cut off to a rune boundary, and
  familyDescription capitalizes the first rune rather than the first
  byte, so neither can emit invalid UTF-8.
- guideToMarkdown no longer repeats the title when a body is only its
  title line.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>

@josephschorr josephschorr left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@samkim
samkim merged commit 984991d into main Oct 23, 2026
10 checks passed
@samkim
samkim deleted the site-metadata branch October 23, 2026 22:34

This branch was successfully deployed

1 active deployment
Preview — 38738a0c Deployed Oct 23, 2026 by vercel[bot]
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