Compress specs to point at code as source of truth#106
Conversation
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>
Deploying mouseterm with
|
| Latest commit: |
063857e
|
| Status: | ✅ Deploy successful! |
| Preview URL: | https://f4e91ba4.mouseterm.pages.dev |
| Branch Preview URL: | https://spec-compress.mouseterm.pages.dev |
dormouse-bot
left a comment
There was a problem hiding this comment.
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,bodysent in reply top=?is bytes-on-the-wire that a calling program can test against. It's now only inOSC99_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 patternProgress <n>%are user-visible external-interface text; now onlyringOrSuppressProtocolProgress/completeProtocolProgress. (These are private methods ofAlertManager, 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.
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)AlertState/ActivityNotification/SessionStatustype blocks with refs toalert-manager.tsandactivity-monitor.ts.cfg.alerttimer table and OSC 99 TTL/cap constants with refs tocfg.tsandterminal-protocol.ts.bellIconClass.TOUCH_MODES,KEYBOARD_MODES,RADIUS_*,MOBILE_TERMINAL_KEY_SEQUENCES,MOBILE_GESTURE_GROUPS, etc.) with refs toMobileTerminalUi.tsxandmobile-gesture-menu.ts.session-types.ts.WebviewMessage/ExtensionMessageunions, keeping only the non-obvious contracts (dormouse:openExternal,pty:data,pty:replay,dormouse:newTerminal).package.json,webview-html.ts, andrelease.yml.Idiom standardization + further cleanup (
b1fb0e8,675ddb4,bd766c1,2eac6d9,5fc3eb4,9cd7f71,3ba8c67,5e98ac1)ActivityMonitorpointer); the verbatim state-machine bullets that re-stated code logic are gone.dragHat,unitToGroup,clampformulas) with one paragraph of design intent and a pointer torootGroupOpacity().computeDynamicPalette().AGENTS.md guardrails (
fa5ccb5,69c3304)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
WebviewMessage/ExtensionMessagenon-obvious contracts, deploy.md artifact filenames) still describe the full bytes-on-the-wire / files-we-ship contract🤖 Generated with Claude Code