Skip to content

docs: relabel the three /docs/deployment index links to the page's own title - #10480

Merged
os-zhuang merged 1 commit into
mainfrom
claude/issue-8984-deployment-index-link-labels
Aug 21, 2026
Merged

docs: relabel the three /docs/deployment index links to the page's own title#10480
os-zhuang merged 1 commit into
mainfrom
claude/issue-8984-deployment-index-link-labels

Conversation

@os-zhuang

@os-zhuangos-zhuang commented Aug 21, 2026

Copy link
Copy Markdown
Contributor

Fixes: #8984

Three pages outside the deployment section linked the section index under labels naming neither of that index's two lifecycles. This is the relabel the card describes — labels only. No link target, heading, page structure or meta.json title was touched.

The two lifecycles, read off the target page

/docs/deployment resolves to content/docs/deployment/index.mdx, titled Deployment Overview. Its own ## headings fork the section in two:

The index's headingWhat it covers
The platform runtime — you operate itThe version-locked train shipped as ghcr.io/objectstack-ai/objectstack. Moved by moving the image tag and restarting. Docker, Compose, Kubernetes, bare Node.js and ObjectStack Cloud are venues inside this half — the page says so explicitly: "Where it runs … is a detail inside the first of those two, not a third thing alongside them."
Your metadata app — you build itThe app you build, compiled to dist/objectstack.json, versioned by your own catalog. Reaches a running platform by catalog install or artifact-pinned boot.

Both replacement labels are checkable against those headings, which is the point: the defect was labels chosen without reference to the target.

The three relabels, in their surrounding clause

1. content/docs/ui/setup-app.mdx:125 — a bullet in ## Related, siblings have no trailing period:

-- [Cloud Deployment](/docs/deployment) — how Setup behaves in cloud mode+- [Deployment Overview](/docs/deployment) — the platform-runtime lifecycle that serves Setup; ObjectStack Cloud is one venue inside it

The old clause promised "how Setup behaves in cloud mode", which the index does not deliver — it has no Setup-specific content, and cloud appears nowhere else in this page except one table cell. The new clause names the half and corrects the premise that cloud is a separate mode.

2. content/docs/automation/hook-bodies.mdx:346 — a bullet in ## See also, siblings do end with a period:

-- [Cloud Deployment](/docs/deployment) — how artifacts travel from Studio to objectos.+- [Deployment Overview](/docs/deployment) — the metadata-app lifecycle: how a compiled artifact reaches a running platform.

"How artifacts travel" is squarely the metadata-app half — the index's "How the app reaches a running platform" table (catalog install vs artifact-pinned boot) is exactly what this reader wants.

3. content/docs/kernel/index.mdx:46 — mid-sentence in a prose **Neighbors:** bullet, so only the label changes; the clause "running the kernel in production" already tells the reader which half they are being sent to:

-- **Neighbors:** … running the kernel in production is covered in [Deployment & Operations](/docs/deployment).+- **Neighbors:** … running the kernel in production is covered in [Deployment Overview](/docs/deployment).

Deployment & Operations is the section title from content/docs/deployment/meta.json; the page is Deployment Overview. Both strings live in the nav, which is what made this one hard to notice.

Census: was it exactly three?

The card found three while doing something else and did not claim the census was exhaustive. It was swept.

Positive control first — before trusting any zero-hit, the expression was proven to find the three known instances:

$ grep -rn '(/docs/deployment)' content/docs/ui/setup-app.mdx content/docs/automation/hook-bodies.mdx content/docs/kernel/index.mdx
content/docs/ui/setup-app.mdx:125:- [Cloud Deployment](/docs/deployment) — how Setup behaves in cloud mode
content/docs/automation/hook-bodies.mdx:346:- [Cloud Deployment](/docs/deployment) — how artifacts travel from Studio to objectos.
content/docs/kernel/index.mdx:46:- … covered in [Deployment & Operations](/docs/deployment).

Then the whole tree, with a pattern that matches the index itself and not its subpages — /docs/deploymentnot followed by/, a word character, or -.

The run used grep -rnP with a negative lookahead. GitHub's body sanitizer strips the exclamation mark out of that construct, so the literal cannot be carried in this text; the POSIX form below was verified to produce byte-identical output (9 lines each, diff clean) and is the one to copy:

$ grep -rnE '/docs/deployment([^/[:alnum:]_-]|$)' content/

9 links across 8 files — 3 defective, 1 examined and cleared, 5 already correct. Nothing outside content/ links the index (the same expression over *.md, *.mdx, *.ts, *.tsx, *.json excluding node_modules returned nothing). There are no trailing-slash (/docs/deployment/) or fragment (/docs/deployment#…) forms.

#SiteLabelVerdict
1ui/setup-app.mdx:125Cloud Deploymentfixed
2automation/hook-bodies.mdx:346Cloud Deploymentfixed
3kernel/index.mdx:46Deployment & Operationsfixed
4api/environment-routing.mdx:128Deployment Overviewalready correct
5index.mdx:51a Card component, title="Deployment & Operations"examined, left alone — see below
6deployment/single-project-mode.mdx:113Deployment Overviewalready correct
7deployment/self-hosting.mdx:14Deployment Overviewalready correct
8deployment/self-hosting.mdx:436Deployment Overview + a clause naming both lifecyclesalready correct — the in-repo precedent these three now follow
9deployment/publish-and-preview.mdx:221Deployment Overviewalready correct

Why row 5 is not a fourth fix

content/docs/index.mdx:51 is one card in the ## Platform modules grid, and that grid uses section titles for section-root links throughout — including where they diverge from the landing page's title:

Card label (section title)Page it lands on
Views & Apps/docs/uiUI Engine
API & SDK/docs/apiAPI Overview
Deployment & Operations/docs/deploymentDeployment Overview

Changing only the deployment card would break a deliberate, uniform convention across nine cards — and re-titling the grid is a restructure, not a relabel. Left as-is on purpose.

Out-of-scope finding, filed not fixed

The sweep turned up the same shape against a different target, on the very same line as fix 3: [Plugins & Packages](/docs/plugins) labels a page whose own title is Plugin System. It is not fixed here — different link target, and whether it is even wrong depends on an unmade judgement (section reference vs page reference) that the grid convention above actively argues both ways on. Filed unassigned as #10476 with both readings laid out. Naming it explicitly so the untouched label on an edited line does not read as an oversight.

Changeset: none, judged by publish surface

Checked rather than defaulted. content/ sits outside every workspace glob in pnpm-workspace.yaml (packages/*, packages/*/*, apps/*, examples/*); the only consumer is apps/docs, which is "private": true and publishes nothing. These three files are not a published package surface, so this PR releases nothing and carries the skip-changeset label instead.

Gates

All of the below were run after the final commit and measured at 6cdb7a9c10 with a clean working tree.

Gate families derived with node scripts/pm/dispatch-gates.mjs (no paths passed — it derives its own change set from the merge base), re-derived at the final commit: the same 12 families, no additions. All green, plus check:nul-bytes.

GateIts own verdict line
check:doc-anchors✅ check-doc-anchors: 256 internal #fragment link(s) across 400 source file(s) all resolve to a real heading
check:docs-redirectscheck-docs-redirects: OK (apps/docs/redirects.mjs: 92 entries -- 89 page destination(s) resolved against content/docs …)
check:runtime-services-index✓ check-runtime-services-index: 8 chapter page(s) vs meta.json "pages", 8 chapter-list bullet(s) and 8 kernel/index.mdx table row(s) … all enumerations agree
check:docs-audit-scope✓ docs-accuracy-audit scope is in sync with content/docs/: 181 hand-written doc(s).
check:role-wordcheck-role-word: OK, no new occurrences of the reserved word.
check:published-readme-links✓ check:published-readme-links — 152 outbound link(s) across 60 published markdown file(s)
check:cross-package-test-inputsexit 0 (also run raw as node scripts/check-cross-package-test-inputs.mjs)
spec: check:liveness · check:empty-state · check:strictness-ledger · check:variant-docsall — each echoed @objectstack/spec@17.1.0 check:…, so none was a zero-match --filter no-op
check:nul-bytescheck-nul-bytes: OK (scanned 6141 text file(s) … no raw ASCII control bytes).

lychee link-checking runs in CI and is not reproducible locally; no link target changed, so no destination moved.


Generated by Claude Code

…n title
Three pages outside the deployment section linked the section index under
labels naming neither of its two lifecycles. The target page is titled
"Deployment Overview" and forks into "The platform runtime — you operate it"
and "Your metadata app — you build it".
- ui/setup-app.mdx and automation/hook-bodies.mdx said "Cloud Deployment".
The page is not cloud-specific; ObjectStack Cloud is one venue inside the
platform-runtime half. Both now use the page title plus a trailing clause
naming which half the reader is sent to.
- kernel/index.mdx used the section title ("Deployment & Operations", from
content/docs/deployment/meta.json) as the label for the page. Both strings
live in the nav, which is what made the mismatch hard to notice.
Labels only — no link target, heading or page structure changed.
Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01DdCnBGcHeufjrq7drTD3wt
@github-actionsgithub-actionsBot added size/xs documentation Improvements or additions to documentation labels Aug 21, 2026
@os-zhuangos-zhuang added the skip-changeset PR has no user-facing published change; bypasses the changeset gate label Aug 21, 2026 — with Claude
@os-zhuangClaude

Copy link
Copy Markdown
ContributorAuthor

PM review — ⭐ accepted. The census is what lifts this above a three-line edit.

Reviewed against the diff.

You read the target before relabelling, which was the one thing that could have gone quietly wrong. The page is Deployment Overview, forking into "The platform runtime — you operate it" and "Your metadata app — you build it", with Docker/Compose/K8s/Cloud as venues inside the first half. A label chosen without opening that page could easily have named a venue again and repeated the defect in new words.

And each replacement was fitted to its own clause rather than globally substitutedsetup-app's Related bullets take no trailing period, hook-bodies' See-also bullets do, and kernel/index.mdx:46 is mid-sentence prose whose surrounding words ("running the kernel in production") already name the half, so only the label token moved. Three files, +3/−3. A sed would have been wrong in at least two of them.

⭐ The census changed what the card means

The card presented three sites. You swept and found 9 links across 8 files — 3 defective, 1 examined and cleared, 5 already correct — and stated the conclusion plainly: "three was what the card noticed, not the count." The five correct ones all say "Deployment Overview", so the repo already had a convention and these three were the outliers, not the pioneers. Using self-hosting.mdx:436 — which already carries a trailing clause naming both lifecycles — as the in-repo precedent for your two rewritten clauses is better than inventing a phrasing.

Positive control before the zero-hit, as asked: the expression was made to return the three known instances first. And the sweep extended outside content/ (*.md/*.mdx/*.ts/*.tsx/*.json) returning nothing, including trailing-slash and #fragment forms.

⭐ The examined-and-cleared row is the judgement I'd have wanted

content/docs/index.mdx:51 labels its card "Deployment & Operations" — the section title, not the page title — and you left it, because that grid uses section titles for section-root links throughout, including where they diverge (Views & Apps → UI Engine, API & SDK → API Overview). Changing one card would break a uniform nine-card convention, and re-titling the grid is a restructure, not a relabel. ⛔ Correctly out of scope, and recorded rather than silently skipped.

Same restraint on #10476: an adjacent wrong-looking label on the very same line you edited (/docs/plugins → "Plugins & Packages" vs the page's "Plugin System"), filed with both readings because section-reference vs page-reference is an unmade judgement — and named in the PR body so an untouched label on an edited line doesn't read as an oversight. That last touch is the kind of thing that saves a reviewer a round trip.

Verified

  • ✅ ⛔ Labels only — no link target, heading, page structure or meta.json title touched.
  • ✅ ⛔ content/docs/releases/** untouched; record-view-auditing.mdx (held by docs(plugin-audit): document the os serve opt-in, and rule out a config-derived audit options helper #10450) untouched.
  • skip-changeset correct here and reasoned, not assumed: content/ is outside every pnpm-workspace glob and its only consumer apps/docs is private: true.
  • ⚠️ Line drift caught and reported — hook-bodies is at 346 on current main, not the card's 345 (card was written against 8b9eba51b).
  • 12 gate families, and you checked the gates themselves weren't vacuous: the four spec-filtered ones each echoed @objectstack/spec@17.1.0 check:…, "confirming a real run rather than a zero-match --filter no-op that would have exited 0 having run nothing." Applying the anti-vacuity rule to your own verification tooling is the right instinct.
  • ✅ Edits proven on disk in both directions rather than trusted from an editor's exit code.

⚠️ One note on the earlier Check Changeset red: that gate ran at 00:31:44 and skip-changeset landed at 00:32:28 — it re-ran itself at 00:32:32 and returned skipped, correctly. Not your failure, and nothing to do; I briefly miscounted the superseded run as live.

Nothing for you to change. Flipping ready and arming once the last check clears.


Generated by Claude Code

@os-zhuang
os-zhuang marked this pull request as ready for review August 21, 2026 00:41
@os-zhuang
os-zhuang added this pull request to the merge queueAug 21, 2026
Merged via the queue into main with commit 724437cAug 21, 2026
31 of 32 checks passed
@os-zhuang
os-zhuang deleted the claude/issue-8984-deployment-index-link-labels branch August 21, 2026 01:13
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentationImprovements or additions to documentationsize/xsskip-changesetPR has no user-facing published change; bypasses the changeset gate

Projects

None yet

Development

Successfully merging this pull request may close these issues.

docs: three pages link the deployment section index under labels that name neither of its two lifecycles

2 participants

@os-zhuang@claude