ADR-0019 Length ceilings refreshed with real level-1 through level-3 copy
#Context
ADR-0018 bootstrapped @wolf-rayet/content-lint's length-ceiling rule from the real-copy scan as it stood the day StatusIndicator was first retrofitted onto the shared tone mechanism: one real call site per component, all four of StatusIndicator's own real copy expressed through a single level-4 call. 0018's own table records level 1 as carrying no real string and no ceiling.
That was true when 0018 was written and stopped being true within the same phase, before 0018 could have known: StatusIndicator's Storybook Contract story gained three more real statusIndicatorTone() calls, at levels 1, 2 and 3, restoring a level-3 string ("Batch 4472 · variance") that had been sitting unwired in a different specimen in the same file and adding two new ones. The real-copy scan now measures 13 real strings across all seven components, up from 10, with level 1 represented for the first time. 0018's table is now wrong about level 1 specifically, and its Consequences section already names this as the expected shape of its own obsolescence: "a bootstrap value ... expected to be superseded once more real copy exists to measure."
#Decision
The derivation method is unchanged from ADR-0018: each level's ceiling is the longest real string the real-copy scan measures shipping at that level, rounded up to the next multiple of ten. This ADR only refreshes the measured values against the corpus as it stands on disk today, read fresh from a live run of pnpm content-lint:scan rather than retyped from 0018 or from memory:
| Level | Longest real string measured | Length | Ceiling |
|---|---|---|---|
| 1 | "Line 2 nominal" (StatusIndicator) | 14 | 20 |
| 2 | "Batch 4471 · label mismatch" (QueueItem) | 27 | 30 |
| 3 | "Enter a complete email address." (InputField) | 31 | 40 |
| 4 | "Clear the jam at the seal press, then release the line." (Alert) | 55 | 60 |
Level 1 is new since 0018. Levels 2 through 4 are unchanged in value from 0018 — StatusIndicator's new level-2 and level-3 strings ("Line 4 running warm", 19 characters; "Batch 4472 · variance", 21 characters) are both shorter than the strings that already set those ceilings, so the numbers hold, only the evidence set behind them grew. Every level now has real copy behind its ceiling; none is open.
packages/content-lint/data/length-ceilings.json already carries these exact four values as of the commit that added StatusIndicator's level-1 call — this ADR is the decision record for a change to the data file that had already landed, not a change made by this record. The rule (length-ceiling) and its read-from-a-data-file mechanism are untouched.
#Rejected options
Re-edit ADR-0018 in place to update its table. What it had going for it: one file instead of two, and no register churn. Rejected because closed ADRs in this system are never silently amended — the register's own convention (README.md: "Closed decisions are never edited; they are superseded") applies exactly as much when only the *data* changed as when the *method* did. An ADR is a record of what was decided and why, on the date it was decided; overwriting 0018's table would make it lie about what was known on 2026-08-31 without a diff anyone reviewing history would notice unless they went looking for exactly this kind of edit.
#Consequences
Same as ADR-0018: this remains a bootstrap value, not a final one. It moves again the next time real copy changes what the scan measures — a longer real string at any level raises that level's ceiling on the next refresh: either a further superseding ADR once the delta is worth recording, or, for routine growth, whatever cadence a future unit decides is worth writing down before it starts happening on every commit that touches a story's copy. That decision is not made here.
ADR-0018's own status line is updated to Superseded by ADR-0019, per the register's convention; 0018's content is left otherwise untouched, as the rejected option above requires. docs/adr/README.md and PLAYBOOK.md §15 both gain this ADR's row and update 0018's, each in its own existing status convention.
Enforcement: touches nothing new in the enforcement table. length-ceiling already runs; this ADR only re-grounds the numbers it enforces.