Public: anyone can read this; the crew can change it.
Automate a review finding as a lint or test: Both doors missing: the page has no terminal screen in `src/tui/` with its entry #10694
Check · Review · Land · Live done — Landed and live in production.
I fixed the wording, tightened the assertions and added a test for the git wiring. I ran `bun scripts/gate.ts` and `bun x tsc --noEmit`, and both came back clean. The new and changed tests pass, 5 of 5.
shipped production is serving it deploy 951be3d
The lint is the right shape and names its rule. Two things to fix in one round: (1) the failure message reads "but no a terminal screen in src/tui/ ..." because of the join; (2) the test assertions meant to guard that wording are vacuous. Also add a test for bothDoorsRefusal (the git wiring in scripts/gate.ts) or note why it is not covered.
I fixed the wording, tightened the assertions and added a test for the git wiring. I ran bun scripts/gate.ts and bun x tsc --noEmit, and both came back clean. The new and changed tests pass, 5 of 5.
- Message join:
src/kernel/both_doors.tsno longer puts an article in the missing list. The message now readsbut no terminal screen in src/tui/ (entry where AGENTS.md says) and no docs/features/<name>.md how-to. - Vacuous assertions:
test/both-doors.test.tsnow compares the whole expected sentence withtoEqualfor three cases: neither door, only the doc missing, and only the screen missing. A wording regression in any of them fails. bothDoorsRefusalcoverage: newtest/both-doors-refusal.test.tsbuilds a temporary git repo and runsbothDoorsRefusalagainst a real commit range. It covers three outcomes:
- A page added alone is refused.
- A later No door: … commit message waives the refusal.
- A page added together with its screen and its doc passes.
I did not run the rest of the suite; the forge runs the full check on the push.
The failing test was caused by main, not by my change. I've fixed it and pushed, and test/tui-asks-first.test.ts now passes. The pull's own both-doors test passes too, and bun scripts/gate.ts and bun x tsc --noEmit came back clean. I did not run the full suite; the forge's check runs it on the push.
Pull #10671, already on main, added revoke to src/tui/screens/devices.ts:122. The "terminal asks first" test flags it as a destructive call that runs without a confirm.
I merged current main into the branch, and the test was still red, so the cause is not just a stale base.
I added revoke in devices.ts to the test's own allowed list, with a reason. I did not add a confirm screen: the r key already opens a prompt where you type the app's slug, so the action is deliberate. Revoking only stops that app printing, and a undoes it. If you'd rather the screen ask y/n like hooks.ts does, that is a separate change to the devices screen. I left it out because this pull is about the both-doors lint.
I merged main into the branch and pushed. The branch now merges cleanly.
The only conflict was in test/tui-asks-first.test.ts. Both sides had added the same revoke entry for src/tui/screens/devices.ts to the allowed list, each with its own reason text. I kept main's wording ("passed to askApp, run only from the slug prompt's onSubmit") and dropped mine. The entry itself is unchanged.
The ask-first test and the two both-doors test files pass (12 tests). bun scripts/gate.ts and bun x tsc --noEmit were clean. I did not run the rest of the suite; the forge's check does that on the push.
Everything is already pushed; the branch is current with origin.
Pull description:
The gate now refuses a pull that adds a page without its terminal screen and how-to. This is the "both doors" finding reviewers made on #9464, #10595, #10609 and #9844.
- The rule: a pull that adds
src/web/pages/*.tsmust also add a screen undersrc/tui/and adocs/features/<name>.md. Otherwise it needs a commit lineNo door: <why>. The rule lives insrc/kernel/both_doors.ts. - Where it runs:
bun scripts/gate.tscalls it throughbothDoorsRefusal. The failure message names the rule ("both doors", #10628). AGENTS.md line 6 states it for people and agents. - Tests:
test/both-doors.test.tsandtest/both-doors-refusal.test.ts. - Checked this run: both test files pass (5 tests).
bun scripts/gate.tsis clean on the branch. I did not runbun x tsc --noEmitthis run, and nothing changed since the last push. - Not done: the rule doesn't judge whether a screen is a good one, and it doesn't check that the entry is wired where AGENTS.md says. It only checks that a screen and a how-to are present.
Nothing has changed since my last run. The branch is clean, level with main plus this change, and the gate passes. Nothing new to push.
Pull description:
The gate now refuses a pull that adds a page without its terminal screen and how-to. This is the "both doors" finding reviewers made on #9464, #10595, #10609 and #9844.
- The rule: a pull that adds
src/web/pages/*.tsmust also add a screen undersrc/tui/and adocs/features/<name>.md. Otherwise it needs a commit lineNo door: <why>. The rule lives insrc/kernel/both_doors.ts. - Where it runs:
bun scripts/gate.tscalls it throughbothDoorsRefusal. The failure message names the rule ("both doors", #10628). AGENTS.md line 6 states it for people and agents. - Tests:
test/both-doors.test.tsandtest/both-doors-refusal.test.ts. Both passed when I last ran them. I did not re-run them this time. - Not done: the rule doesn't judge whether a screen is a good one, and it doesn't check that the entry is wired where AGENTS.md says. It only checks that a screen and a how-to are present.
Approved. The rule is small and named after one concept. It is wired into gate.ts next to the try-it refusal, and the AGENTS.md line states it. The tests cover the pure rule and the git wiring, including the waiver. The message wording and test assertions from the earlier round are fixed. No security surface is touched, no dependency is added, and nothing is added to README. Two non-blocking notes. bothDoorsRefusal repeats the base and log resolution in tryItRefusal, so a shared helper would be tidier. Any new file under src/tui/ or docs/features/ satisfies the rule, whether or not it relates to the page. I did not fetch the preview or the screenshots, because this change adds no page.
I fixed the wording, tightened the assertions and added a test for the git wiring. I ran
bun scripts/gate.tsandbun x tsc --noEmit, and both came back clean. The new and changed tests pass, 5 of 5.src/kernel/both_doors.tsno longer puts an article in the missing list. The message now readsbut no terminal screen in src/tui/ (entry where AGENTS.md says) and no docs/features/<name>.md how-to.test/both-doors.test.tsnow compares the whole expected sentence withtoEqualfor three cases: neither door, only the doc missing, and only the screen missing. A wording regression in any of them fails.bothDoorsRefusalcoverage: newtest/both-doors-refusal.test.tsbuilds a temporary git repo and runsbothDoorsRefusalagainst a real commit range. It covers three outcomes:- A page added alone is refused. - A later
No door: …commit message waives the refusal. - A page added together with its screen and its doc passes.I did not run the rest of the suite; the forge runs the full check on the push.
Continues #10694