From f2e2509167a51a00ff6d9c7f08c692a265690a2a Mon Sep 17 00:00:00 2001 From: Doxa Maps Date: Mon, 28 Sep 2026 08:45:40 +0000 Subject: [PATCH] documentation: the browser guard, and ask the repo rather than grepping Follow-up to the doc landing in 49, which was written before the guard existed. Adds the guard: every browser gate reaches Playwright through internal/lib/playwright-guarded.mjs and refuses unless browser-slot.sh exported DOXA_BROWSER_SLOT; an unslotted run exits 75 with the command to use, quoted verbatim. And says the slot is a COUNTING SEMAPHORE, not a mutex, with the reason from its own header -- a single lock queued 10-19 deep for hours because the real constraint is memory, ~300-500MB per chrome, not exclusivity. Replaces the grep advice with `bun run browser-gates`. The grep still works and is fine for a quick look, but it is a heuristic over file text: my own count from grepping internal/check-*.mjs said 87 browser gates; the repo's own detector says 97, because browser gates also live in plugin-designs/*/scripts/. Corrected. The authoritative list cannot drift from what is enforced, because check:browser-gates-guarded uses the same detector. One line the guard's header earns and this doc had not stated: being able to launch is not the same as it being yours to launch. The guard stops the accident; it does not hand a newcomer the seat. Testing whether the guard refuses is itself a browser launch. Does NOT claim path-into-node_modules detection: studio has that in landing 50, and it is not in this tree, so the doc does not describe it yet. --- .../HOWTO-which-gates-need-a-browser.md | 48 ++++++++++++++++--- 1 file changed, 41 insertions(+), 7 deletions(-) diff --git a/documentation/HOWTO-which-gates-need-a-browser.md b/documentation/HOWTO-which-gates-need-a-browser.md index 45a8bb0c4..484202561 100644 --- a/documentation/HOWTO-which-gates-need-a-browser.md +++ b/documentation/HOWTO-which-gates-need-a-browser.md @@ -1,6 +1,6 @@ # Which gates need a browser -There are **238** checks in this repo. **148 run anywhere. 87 need a real browser.** If you are not +There are **238** checks in this repo. **97 need a real browser**; the rest run anywhere. If you are not the person who owns the browser seat, that second group is not yours to run — and knowing which is which saves you from a whole class of wrong answer. @@ -12,14 +12,16 @@ which saves you from a whole class of wrong answer. ## Telling them apart -Open the gate's file and look for one import: +**Ask the repo, don't grep:** ```bash -grep -l 'playwright\|chromium' internal/check-*.mjs +bun run browser-gates # lists every script that launches a browser ``` -If it imports `playwright` or launches `chromium`, it needs a browser. That is the whole test — the -name does not tell you. `check:packet-render` sounds like a file check and drives a browser; +That is the authoritative answer — the same detector `check:browser-gates-guarded` uses, so it +cannot drift from what is enforced. A grep for `playwright|chromium` also works today and is fine +for a quick look, but it is a heuristic: it finds files that *mention* the word, and it would miss a +file that reached the package by path. The name tells you nothing either. `check:packet-render` sounds like a file check and drives a browser; `check:composites-mount` sounds like it needs one and does not (it mounts every composite through Vite's SSR loader, no browser at all). @@ -27,8 +29,8 @@ Vite's SSR loader, no browser at all). | | Count | |---|---:| -| headless — run these yourself | **148** | -| **browser — not yours unless you own the seat** | **87** | +| headless — run these yourself | the remainder | +| **browser — not yours unless you own the seat** | **97** | | neither (shells out to `bun`/`php`) | 3 — `check:mobile`, `check:wp-embed`, `smoke:playground` | The browser group is, broadly: everything that renders a map (`check:map-paints`, @@ -60,6 +62,38 @@ and confusing them is the most common way to report something false: --- +## The guard: you cannot launch a browser by accident any more + +The rule above used to be remembered. It is now **enforced**. Every browser gate reaches Playwright +through `internal/lib/playwright-guarded.mjs`, which refuses to launch unless +`internal/browser-slot.sh` has exported `DOXA_BROWSER_SLOT`: + +```bash +internal/browser-slot.sh bun run check:packet-render # the only way to run one +``` + +Run a browser gate outside the slot and it does not fail — **it exits 75 and tells you the command**: + +``` +this gate launches a browser. Browsers run only on the browser seat, inside the slot: + internal/browser-slot.sh bun run