Skip to content

Compress specs to point at code as source of truth#106

Merged
nedtwigg merged 15 commits into
mainfrom
spec-compress
May 28, 2026
Merged

Compress specs to point at code as source of truth#106
nedtwigg merged 15 commits into
mainfrom
spec-compress

Conversation

@nedtwigg
Copy link
Copy Markdown
Member

Summary

Trims the docs/specs/* files by pointing at code, scripts, and config as the source of truth wherever the spec was duplicating something already canonical there. Net −365 lines across 9 specs (514 deleted, 149 added) with no contract content removed — only inline copies of TypeScript types, timer tables, CI workflow steps, NSIS path tables, opacity-math transcriptions, and similar.

The 14 commits land in three groups:

Initial compression (71effa2, 526470c, ad75034, e9e7ccd)

  • Replace inline AlertState / ActivityNotification / SessionStatus type blocks with refs to alert-manager.ts and activity-monitor.ts.
  • Replace the cfg.alert timer table and OSC 99 TTL/cap constants with refs to cfg.ts and terminal-protocol.ts.
  • Replace inline bell-icon visual mapping with ref to bellIconClass.
  • Replace inline mobile-gesture tables (TOUCH_MODES, KEYBOARD_MODES, RADIUS_*, MOBILE_TERMINAL_KEY_SEQUENCES, MOBILE_GESTURE_GROUPS, etc.) with refs to MobileTerminalUi.tsx and mobile-gesture-menu.ts.
  • Replace inline persisted-session interfaces and v1→v2→v3 migrations with ref to session-types.ts.
  • Replace the full webview ↔ host message-type tables with refs to WebviewMessage / ExtensionMessage unions, keeping only the non-obvious contracts (dormouse:openExternal, pty:data, pty:replay, dormouse:newTerminal).
  • Replace inline VS Code extension manifest, CSP directives, and CI workflow steps with refs to package.json, webview-html.ts, and release.yml.

Idiom standardization + further cleanup (b1fb0e8, 675ddb4, bd766c1, 2eac6d9, 5fc3eb4, 9cd7f71, 3ba8c67, 5e98ac1)

  • Standardize all standalone source-pointer sentences to the same `Source of truth: X in Y defines Z` idiom across 7 specs. Inline parentheticals stay as natural prose.
  • Compress alert.md `WATCHING` transition mechanics to the invariants the implementation must honor (with ActivityMonitor pointer); the verbatim state-machine bullets that re-stated code logic are gone.
  • Replace mobile-ui.md's verbatim opacity-math (dragHat, unitToGroup, clamp formulas) with one paragraph of design intent and a pointer to rootGroupOpacity().
  • Fold mouse-and-clipboard.md §1.1/1.2/1.3 and §2.1-2.6 micro-sections into fewer headers with bold-labeled paragraphs.
  • Merge the two paragraphs in theme.md that both named computeDynamicPalette().
  • Add the glossary blockquote callout to specs that use Session/Pane/Door vocabulary but lacked it (alert, mobile-ui, mouse-and-clipboard, vscode).
  • Drop the 14-bullet Verification Checklist from alert.md — every bullet was a verbatim restatement of a rule given earlier in the same file.

AGENTS.md guardrails (fa5ccb5, 69c3304)

  • "Keep specs concise but do not replace invariants or edge cases with only a code pointer. Use `Source of truth:` for implementation references, and include direction/scope for protocols, command orchestration, and cross-package boundaries. For docs-only compression, spot-check referenced symbols, message directions, and root-vs-package script ownership against code before committing."
  • "Wire-protocol and external-interface sections are themselves the contract — keep the full specification (sequences, fields, named files, signing inputs) even when a parser or script implements them."
  • "Every spec that uses Session / Pane / Door / baseboard / passthrough vocabulary leads with a glossary blockquote callout."
  • Also restored one WATCHING-transition edge-case bullet (`First output starts candidate tracking without changing status; unconfirmed MIGHT_BE_BUSY returns to NOTHING_TO_SHOW; ALERT_RINGING ignores new output until the Session has attention`) that the initial compression had over-cut.

A multi-agent verification pass at `xhigh` effort confirmed every code reference in the compressed text resolves to an existing symbol with matching semantics; the only finding was a wording ambiguity ("matched first" → "matched before") in the smart-token PATTERNS reference, fixed in 675ddb4.

Test plan

  • Read each touched spec end-to-end and confirm it still reads as a complete contract, not a stub
  • Confirm every `Source of truth:` pointer resolves: the named file exists and the named symbol is exported / present
  • Confirm wire-protocol sections (OSC 9 / 9;4 / 99 / 777 / BEL, WebviewMessage / ExtensionMessage non-obvious contracts, deploy.md artifact filenames) still describe the full bytes-on-the-wire / files-we-ship contract
  • Confirm the glossary callout pattern is consistent across specs that use Session vocabulary

🤖 Generated with Claude Code

nedtwigg and others added 14 commits May 27, 2026 20:27
Replace verbatim copy/data/config that is canonical in code with one-line
pointers to the owning file/symbol, across nine specs:

- alert.md: type blocks, timer-defaults table, bell-visual table, notification
  literals, magic numbers -> alert-manager.ts / terminal-protocol.ts / cfg.ts
- transport.md: message-type tables, persisted-session interfaces ->
  message-types.ts / session-types.ts (kept contract-bearing messages)
- deploy.md: CI matrix/step narration, expected-path and filename tables ->
  release.yml / sign-and-deploy.sh (kept security rationale + checklists)
- vscode.md: manifest, CSP, build-pipeline blocks -> package.json /
  webview-html.ts / launch.json
- mobile-ui.md: gesture/radii/mode tables, placeholder copy ->
  MobileTerminalUi.tsx / mobile-gesture-menu.ts
- mouse-and-clipboard.md: hover/hint/button strings, smart-token patterns
- terminal-state.md: status-bucket and grouping tables -> terminal-state.ts
- theme.md: token-binding table, Storybook default literal
- layout.md: dormouseTheme constants

Glossary, terminal-escapes, and shortcuts are left intact: they are curated
source-of-truth references, not duplication. All cross-spec anchors preserved.
Sweep the standalone source-pointer sentences in alert.md, mobile-ui.md,
mouse-and-clipboard.md, terminal-state.md, theme.md, transport.md, and
vscode.md to the same "Source of truth: X in Y defines Z" form introduced
in b1fb0e8. Inline parentheticals stay as natural prose. Also clarifies
the ambiguous smart-token "matched first" phrasing to "matched before".

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Replace the per-field internal-state-track bullets and the 7-line WATCHING
transition list with the design intent + invariants, plus a source-of-truth
pointer to ActivityMonitor. The transition mechanics live in code; the
spec only needs to state the invariants the implementation must honor
(ring on fresh transition only, attention suppression, latch behavior,
attended-output starts a fresh cycle).

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
The dragHat/unitToGroup/clamp/blend formulas were a verbatim transcription
of rootGroupOpacity() in MobileGestureRadialMenu.tsx. Replace with a
one-paragraph design intent (align-with-drag fades the off-axis groups,
threshold at RADIUS_FADE_START, full effect at RADIUS_SELECT) and a
source-of-truth pointer.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
§1 had three two-line subsections (Visibility/Hover/Click); fold into one
section with bold-labeled paragraphs. §2 split a single override-state
contract into six numbered subsections (2.1-2.6); fold into a single
section organized by override mode (temporary, sticky) with end-conditions
and cross-cutting rules as bold-labeled paragraphs. Same content, fewer
headers.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Lines 20 and 22-27 both named computeDynamicPalette and overlapped on what
it does. Merge into a single paragraph that names the function, its
location, its OKLab helpers, the publish hook, and the public-helper export,
then leads into the existing pick-rules bullet list.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Adds the > See docs/specs/glossary.md... opening callout to alert.md,
mobile-ui.md, mouse-and-clipboard.md, and vscode.md, matching the pattern
already in layout.md and terminal-state.md. transport.md already
references glossary.md in its existing opening callout, so no change there.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Every checklist item restated a rule already given verbatim earlier in
the file: fresh-transition rule from WATCHING Track, Pane↔Door
persistence from §Public State, Door click vs d from §UI Contract,
attention-suppression and protocol-wins precedence from §Command-exit
Track, replay filtering from §Public State, long-title truncation from
§UI Contract, etc. Removing leaves the spec rules as the single statement
of each contract; no other spec carries this kind of checklist.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Two follow-on rules on top of the existing "preserve invariants and edge
cases" paragraph:

1. Wire-protocol and external-interface sections (terminal-escapes.md,
   transport.md tables, alert.md OSC sequences, deploy.md artifact tables)
   are themselves the contract — keep the full spec, not just a code
   pointer.

2. Every spec that uses Session / Pane / Door vocabulary leads with the
   glossary blockquote callout; introducing glossary vocabulary into a
   spec that lacks the callout means adding it in the same edit.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@cloudflare-workers-and-pages
Copy link
Copy Markdown

cloudflare-workers-and-pages Bot commented May 28, 2026

Deploying mouseterm with  Cloudflare Pages  Cloudflare Pages

Latest commit: 063857e
Status: ✅  Deploy successful!
Preview URL: https://f4e91ba4.mouseterm.pages.dev
Branch Preview URL: https://spec-compress.mouseterm.pages.dev

View logs

Copy link
Copy Markdown
Collaborator

@dormouse-bot dormouse-bot left a comment

Choose a reason for hiding this comment

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

Spot-checked the references — every symbol/file the compressed text points at resolves (AlertState/ActivityNotification in alert-manager.ts, ActivityMonitor/SessionStatus in activity-monitor.ts, the RADIUS_*/MOBILE_GESTURE_* constants, groupTerminalPanes/statusBucket, WebviewMessage/ExtensionMessage, PersistedSession, FNAME_*, getNonce, PREFERRED_STORYBOOK_THEME, etc.). The new AGENTS.md guardrail-pass also catches the resize-debounce invariant (still in alert.md §WATCHING Track, line 53).

One tension worth a second look. The new AGENTS.md rule names "the OSC 9 / 9;4 / 99 / 777 / BEL sequence rules in alert.md" as content that "must keep the full specification — sequences, fields, named files, signing inputs — even when a parser or script implements them." A few of the alert.md deletions in this same PR sit on the wrong side of that line:

  • OSC 99 support response. The literal payload o=always:p=title,body sent in reply to p=? is bytes-on-the-wire that a calling program can test against. It's now only in OSC99_SUPPORT_PAYLOAD (alert.md §OSC 99, "p=? sends a support response advertising the support payload defined in...").
  • OSC 99 pending-chunk TTL / cap. "60 seconds" and "64 pending ids" are observable wire-level behavior (slow chunked OSC 99 traffic gets dropped) — now only described as "defines the pending OSC 99 chunk TTL and max-pending-id cap."
  • OSC 9;4 generated notification strings. Progress complete, Progress warning, Progress error, and the body pattern Progress <n>% are user-visible external-interface text; now only ringOrSuppressProtocolProgress / completeProtocolProgress. (These are private methods of AlertManager, so a reader follows the pointer and lands inside the class.)

Similarly, transport.md's full webview ↔ host message-type enumeration is now a 4-row "non-obvious contracts" table. The names are mostly self-explanatory, but the new AGENTS.md text specifically calls out "the message-protocol tables in transport.md" as something that must keep the full spec; the table that's there now is a deliberate subset.

Two reasonable resolutions, your call: either restore the OSC 99 wire-protocol pieces (the support payload + the TTL/cap numbers) inline in alert.md and the full message table in transport.md, or soften the AGENTS.md wording so the rule matches what this PR actually keeps (e.g. "keep the full specification for fields and named files that aren't self-describing" — which would license the message-table subset and the generated-title pointers, while still mandating the explicit wire literals).

Not approving on this commit because I'd like the maintainer to land on which side the rule should fall — but no concerns beyond this one.

@nedtwigg nedtwigg merged commit 4b9499e into main May 28, 2026
6 checks passed
@nedtwigg nedtwigg deleted the spec-compress branch May 28, 2026 06:05
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