fix(booth): the reveal button was inert; add kept-lane wipe and in-booth keep
Three operator reports, one of them a real defect I had claimed was working. THE REVEAL BUTTON DID NOTHING, for a day. Its handler sat after the content block's closing tag, and a child template's out-of-block content is silently DISCARDED by Jinja. The button rendered. The handler never reached the browser. Two commits and a README paragraph said click-to-reveal worked, and the suite passed the entire time because nothing asserted against the SERVED page -- the template really did contain the code. Two guards, both confirmed to FAIL when the defect is reintroduced rather than merely added and assumed protective: * test_reveal_handler_actually_reaches_the_served_page greps the response * test_no_orphaned_markup_after_the_content_block guards the structure While moving it, caught a second instance of the same class: the explanatory comment I wrote for the fix contained a literal Jinja endblock tag, which Jinja would have parsed as a real tag and used to close the block early. KEPT-LANE ×. Wiping a kept booth required release-then-find-it-in-the-other- lane. That protected nothing and cost a hunt -- the board you just released is loose in a feed that turns over, and you have to go find it to finish a job you had already decided on. Protection now lives in the confirmation, which names the booth and says KEPT, instead of in the number of lanes you must traverse. Release stays as the reversible option. IN-BOOTH KEEP. `☆ keep` / `★ kept — release` beside "Wipe now", so promoting does not mean navigating back to the index. The booth page did not previously know its own kept state; it does now. Both post a `next` field to stay put -- and `next` is a form field, so it is attacker-controlled: only same-site absolute paths are honoured, with `//host`, schemes and backslashes refused, tested. 173 tests pass.
This commit is contained in:
@@ -70,6 +70,16 @@ figures across mixed kinds and will fail if you don't.
|
||||
tells the truth about whether anything here is blurred.
|
||||
- **Reveal is per-viewer and never persisted.** Click 👁 reveal; a reload
|
||||
re-hides. With JS off it stays blurred, which is the safe direction to fail.
|
||||
|
||||
⚠ This button shipped INERT on 2026-09-20 and stayed that way for a day. Its
|
||||
handler sat after the content block's closing tag, and a child template's
|
||||
out-of-block content is silently DISCARDED by Jinja — the button rendered,
|
||||
the handler never reached the browser, and two commits plus this README said
|
||||
it worked. The suite passed throughout because nothing asserted against the
|
||||
served page. `test_reveal_handler_actually_reaches_the_served_page` now greps
|
||||
the HTTP RESPONSE, and `test_no_orphaned_markup_after_the_content_block`
|
||||
guards the structure. Both were confirmed to FAIL when the defect is
|
||||
reintroduced, which is the only way to know a guard guards anything.
|
||||
- **Covers inherit it.** If a booth's cover image is blurred, the index card's
|
||||
thumb is blurred too — otherwise the front page undoes the censoring.
|
||||
- **Inline docs are blurred too**, not just images and video. That branch puts
|
||||
@@ -77,8 +87,25 @@ figures across mixed kinds and will fail if you don't.
|
||||
|
||||
## Keeping a booth (round trip, both directions)
|
||||
|
||||
`★` on an ephemeral card promotes it to the kept lane; `release` in the kept
|
||||
lane sends it back. Equivalent CLI: `booth keep <name>` / `booth unkeep <name>`.
|
||||
Three places, all doing the same thing:
|
||||
|
||||
- **Index, ephemeral card** — `★` promotes to the kept lane.
|
||||
- **Index, kept card** — `release` demotes, and `×` now WIPES DIRECTLY. The old
|
||||
rule was release-then-find-it-in-the-other-lane; that protected nothing and
|
||||
cost a hunt, because the board you just released is loose in a feed that
|
||||
turns over. Protection lives in the confirmation now, which names the booth
|
||||
and says KEPT.
|
||||
- **Inside a booth** — `☆ keep` / `★ kept — release`, beside *Wipe now*, so you
|
||||
do not have to go back to the index. These post a `next` field to stay on the
|
||||
page; `next` is a form field and therefore attacker-controlled, so only
|
||||
same-site absolute paths are honoured (`//host`, schemes and backslashes are
|
||||
refused).
|
||||
|
||||
Equivalent CLI: `booth keep <name>` / `booth unkeep <name>`.
|
||||
|
||||
⚠ Release BUMPS the directory mtime, so a released board's age resets and it
|
||||
survives another full TTL. Unkeep-and-wait is a 24h delay, not a delete — which
|
||||
is exactly why the direct `×` was worth adding.
|
||||
|
||||
⚠ Until 2026-09-19 the UI only went one way — the kept lane could release, but
|
||||
an ephemeral booth could only be kept from a shell. The `/keep` route and the
|
||||
|
||||
Reference in New Issue
Block a user