Files
booth/persistent-memory.d/2026-09-21-jinja-hot-reload-outage.md
T
Vuong Hoang d37b81ab9f memory: snapshot — U5 released at v0.3.0, and the index goes two-tier
The two dated log sections had never been split, so every one of their 29
entries sat inline and the startup index had grown to 372 lines — which is
the cost the two-tier scheme exists to remove, paid on every session that
reads the file. 27 entries were over threshold. All 29 now have a detail
file under persistent-memory.d/ and a one-line index entry that routes
rather than restates. Index: 372 -> 93 lines.

No archival. The soft cap fired, but every entry in this repo is dated
2026-09-21 or later, so the under-14-days guard held all of them back — and
the split alone took the index well under the target without moving
anything out of the active file.

The in-flight section is rewritten for the post-release state: nothing is
in flight, no gate is outstanding, and the next unit is explicitly recorded
as the operator's undecided call rather than as a plan. The session's
recommendation (U4, on three grounds) is written down so it does not have
to be re-derived, alongside the two alternatives and why they are
alternatives.

Two dated predictions are carried forward with their dates and their
instruments: the U5 adoption re-measure on 2026-09-29, which already reads
3 of 24 announced and 2 with a why from peers told nothing, and the
.forever re-count a fortnight AFTER U4 lands, which is U4's own success
criterion and is destroyed by running it early.
2026-09-22 08:20:51 -07:00

1.5 KiB

Letting Jinja hot-reload templates in the deployment root

2026-09-21 · booth

Letting Jinja hot-reload templates while the repo is the deployment root — the cause of a live outage the same day U2 landed, and the sharpest foot-gun in the repo. booth.service sets WorkingDirectory to this repo, so the running service imports these files with no build step and no staging copy. Python is read once at process start; Jinja's FileSystemLoader re-reads a template on every render. Editing booth.html therefore deployed it instantly against Python from 22:03 that knew nothing about item_marks, and 19 of 25 live booths returned 500 with UndefinedError: 'item_marks' is undefined. Neither the old code nor the new code was broken — the service was running both at once. The lesson that generalises: a skew between a process and the disk under it is invisible to the test suite by construction, so no amount of green tests would have caught it; the operator found it. Fixed at the source rather than with a reminder — the Environment is hand-built with auto_reload=False, so there is now ONE staleness rule (nothing takes effect until you restart) and the running process is always a coherent snapshot of one commit. Asserted by test_templates_do_not_hot_reload_from_disk. Watch the second-order risk the fix introduces: a hand-built Environment does not inherit autoescape from the Jinja2Templates constructor, and booth names, item names and mark text are all agent-authored strings landing in HTML.