7.1 KiB
CONTRACT — gstack-playwright-lib
- date: 2026-09-13 | flow: feat | branch: feature/gstack-playwright-lib
- status: active
REQUEST (verbatim — IMMUTABLE)
Message 1:
l'installation de chromium, c'est une version fix ou en latest ? Il faudrait mettre en lateste, et d'ailleurs son update est pris en compt dans l'update ? quelq version a besoin gstack ? Ca serait pas plus simple d'installer perplexity a la place ?
Message 2 (after the assistant proposed fix A + fix B):
les deux
Message 3 (answer to the scope question on fix B, after the "654 Mo orphelins" premise was proven wrong):
Check read-only dans doctor.sh
CLARIFICATIONS
Q: "mettre en latest" — pin Chromium to latest? A: Not actionable as asked. Playwright downloads the browser revision its own version pins (1.61.1 → chromium 1228); the CDP client is coupled to that build. "Latest" = track the latest Playwright, which is what BDR-029's bump already does. No change to the pinning mechanism is in scope.
Q: Volet B — purge the orphan Playwright revisions?
A: Superseded by evidence. ~/.cache/ms-playwright/.links/ registers THREE
playwright installs (gstack 1.61.1 → rev 1228; gsd-pi nvm 1.61.0 → 1228;
gsd-pi ~/.local 1.63.0 → 1243). Every directory on disk is referenced;
zero bytes reclaimable. Playwright already GCs correctly on every
install (_deleteStaleBrowsers, unions across all registered installs).
User chose: read-only report in doctor.sh, NO deletion anywhere.
ACCEPTANCE CRITERIA
-
lib/gstack-playwright.shexists, is source-safe (sourcing prints nothing and runs no side effect), and its verb dispatcher works when executed. CHECK: out=$( . lib/gstack-playwright.sh; echo READY ); [ "$out" = READY ] && bash lib/gstack-playwright.sh 2>&1 | grep -q 'usage:' && echo LIB_OK EXPECT: LIB_OK EVIDENCE: MET exit=0 marker-found :: LIB_OK -
The bump logic lives ONLY in the lib:
install-plugins.shno longer definesgstack_bump_playwright_if_unsupported, sources the lib instead, and still calls it BEFORE gstack./setup(BDR-029 behavior unchanged: OS-gated, idempotent, non-fatal). CHECK: grep -q '^gstack_bump_playwright_if_unsupported() {' install-plugins.sh && exit 1; grep -q 'lib/gstack-playwright.sh' install-plugins.sh || exit 1; c=$(grep -n 'gstack_bump_playwright_if_unsupported' install-plugins.sh | grep -v '::space:*#' | tail -1 | cut -d: -f1); s=$(grep -n '&& ./setup)' install-plugins.sh | head -1 | cut -d: -f1); [ -n "$c" ] && [ -n "$s" ] && [ "$c" -lt "$s" ] && echo EXTRACT_OK EXPECT: EXTRACT_OK EVIDENCE: MET exit=0 marker-found :: EXTRACT_OK -
update-all.shdelegates the gstack submodule update to the lib (gstack_submodule_update_with_bump) instead of callinggit submodule update --remotebare, so the bump is re-applied after every successful update. CHECK: grep -q 'gstack_submodule_update_with_bump' update-all.sh && grep -q 'lib/gstack-playwright.sh' update-all.sh && ! grep -qE '^:space:*if git submodule update --remote skills-external/gstack' update-all.sh && echo WIRED_OK EXPECT: WIRED_OK EVIDENCE: MET exit=0 marker-found :: WIRED_OK -
[gated 2026-09-15]
gstack_submodule_update_with_bumpNEVER modifies the submodule working tree. On a successfulgit submodule update --remoteit re-applies the bump; on failure it returns non-zero, touches nothing, and emits git's own message plus a hint naming the local Playwright bump whenpackage.json/bun.lockare the dirty files. The conflict-RECOVERY branch of the earlier revision (discard, retry, backup, restore) is withdrawn: it could leave the bump discarded and un-reapplied, regressing a working browser into BLK-008, which the pre-existing behavior never did. CHECK: sed 's/#.//' lib/gstack-playwright.sh | grep -qE 'git [^|;](checkout|reset|clean|stash)' && exit 1; bash lib/tests/gstack-playwright.test.sh 2>&1 | grep -q 'update-conflict' && bash lib/tests/gstack-playwright.test.sh 2>&1 | grep -qE '^PASS=[0-9]+ FAIL=0$' && echo NONDESTRUCTIVE_OK EXPECT: NONDESTRUCTIVE_OK EVIDENCE: MET exit=0 marker-found :: NONDESTRUCTIVE_OK -
doctor.shprints a Playwright-browsers section: total cache size, one line per browser directory naming the registered playwright install(s) that reference it, plus counts of unreferenced directories and broken links. CHECK: bash doctor.sh 2>/dev/null | grep -qi 'playwright browsers' && bash lib/gstack-playwright.sh browsers-report | grep -qE 'chromium-[0-9]+' && bash lib/gstack-playwright.sh browsers-report | grep -qi 'unreferenced' && echo REPORT_OK EXPECT: REPORT_OK EVIDENCE: MET exit=0 marker-found :: REPORT_OK -
The report is provably read-only: no destructive verb anywhere in the lib, and the cache directory listing is identical before and after a report run. CHECK: sed 's/#.*//' lib/gstack-playwright.sh | grep -qwE '(rm|rmdir|unlink|truncate|mv)' && exit 1; b=$(ls -la ~/.cache/ms-playwright ~/.cache/ms-playwright/.links 2>/dev/null | cksum); bash lib/gstack-playwright.sh browsers-report >/dev/null 2>&1; a=$(ls -la ~/.cache/ms-playwright ~/.cache/ms-playwright/.links 2>/dev/null | cksum); [ "$b" = "$a" ] && echo READONLY_OK EXPECT: READONLY_OK EVIDENCE: MET exit=0 marker-found :: READONLY_OK
-
lib/tests/gstack-playwright.test.shexists, passes, and covers at least: bump skipped when the OS tag is already supported; bump fired when it is not; submodule-update conflict recovery; browsers-report on a fixture cache holding a referenced revision, an unreferenced one and a broken link. CHECK: bash lib/tests/gstack-playwright.test.sh | tail -1 | grep -qE '^PASS=[0-9]+ FAIL=0$' && echo TESTS_OK EXPECT: TESTS_OK EVIDENCE: MET exit=0 marker-found :: TESTS_OK -
shellcheck clean on every touched shell file. CHECK: shellcheck lib/gstack-playwright.sh lib/tests/gstack-playwright.test.sh install-plugins.sh update-all.sh doctor.sh >/dev/null 2>&1 && echo SHELLCHECK_OK EXPECT: SHELLCHECK_OK EVIDENCE: MET exit=0 marker-found :: SHELLCHECK_OK
-
[gated 2026-09-15] (judgement) No new dependency; the report degrades silently when
~/.cache/ms-playwrightis absent, when its.linksdirectory is absent, whenPLAYWRIGHT_BROWSERS_PATHis0or not a directory, or when no playwright install is registered — doctor must stay green on a machine that never installed a browser. The lib's printers are named_gspw_ok/_gspw_warn/_gspw_infoand it defines NO bareok/warn/info/pass/fail: doctor.sh sources the lib before every check, so bare names would override its own printers and silently disconnect itsERRORS/WARNScounters.
FILE SCOPE
- lib/gstack-playwright.sh (new)
- lib/tests/gstack-playwright.test.sh (new)
- install-plugins.sh (remove inline fn, source + call lib)
- update-all.sh (call bump + conflict recovery)
- doctor.sh (new read-only report section)
Out of scope: the gstack submodule itself, the pinning mechanism, any
deletion of cached browsers, the GSTACK_CHROMIUM_NO_SANDBOX layer
(LRN-040 layer 2, unchanged).