From a1876928f450ba8eb67431c78527490c7979b157 Mon Sep 17 00:00:00 2001 From: Jason Woltje Date: Thu, 22 Oct 2026 14:06:36 -0500 Subject: [PATCH] Row 286 C2-03b: fold dewey-0869 and sage-2951 (marker-gated busy test, T9 scratch roles with a chief gitea credential, fired-chief path cited) --- .../bus/tests/library-credential.test.mjs | 7 +++++++ packages/library/tests/sync.test.mjs | 20 +++++++++++-------- 2 files changed, 19 insertions(+), 8 deletions(-) diff --git a/packages/bus/tests/library-credential.test.mjs b/packages/bus/tests/library-credential.test.mjs index 2ba0b95d9..51b90ab96 100644 --- a/packages/bus/tests/library-credential.test.mjs +++ b/packages/bus/tests/library-credential.test.mjs @@ -250,7 +250,14 @@ test('C2-03b T9 runtime: the chief\'s store file and user, then a real revoke th const f = repo(t), root = f.root, dataRoot = join(root, 'data'); mkdirSync(dataRoot, { mode: 0o700 }); const storeRoot = join(root, 'secrets', 'agents'); + // A scratch roles/ whose chief-of-staff carries a gitea credential, as row 285 ships it + // (case2-rows.md:1823-1824), so the runtime's definitions match the ones the grant ran under + // (dewey-0869). Rebased onto 285, the copy needs no edit. const rolesDir = rolesCopy(root); + const chiefRole = join(rolesDir, 'chief-of-staff.json'); + const chiefDefinition = JSON.parse(readFileSync(chiefRole, 'utf8')); + if (!chiefDefinition.credentials.some(c => c.service === 'gitea')) chiefDefinition.credentials.push({ service: 'gitea' }); + writeFileSync(chiefRole, JSON.stringify(chiefDefinition, null, 2) + '\n'); const slot = join(root, 'secrets', 'acme', library.SLOT); mkdirSync(join(root, 'secrets', 'acme'), { recursive: true, mode: 0o700 }); writeFileSync(slot, SLOT_TOKEN + '\n', { mode: 0o600 }); diff --git a/packages/library/tests/sync.test.mjs b/packages/library/tests/sync.test.mjs index 076924cec..cbb281052 100644 --- a/packages/library/tests/sync.test.mjs +++ b/packages/library/tests/sync.test.mjs @@ -3,7 +3,7 @@ // argv and adds the CA to its env. The token is made up and must appear nowhere but the slot. import test, { before, after } from 'node:test'; import assert from 'node:assert/strict'; -import { accessSync, chmodSync, constants, mkdirSync, mkdtempSync, readdirSync, readFileSync, rmSync, statSync, symlinkSync, unlinkSync, writeFileSync } from 'node:fs'; +import { accessSync, chmodSync, constants, existsSync, mkdirSync, mkdtempSync, readdirSync, readFileSync, rmSync, statSync, symlinkSync, unlinkSync, writeFileSync } from 'node:fs'; import { tmpdir } from 'node:os'; import { dirname, join } from 'node:path'; import { spawnSync } from 'node:child_process'; @@ -370,23 +370,27 @@ test('C2-03b T2 and T3: a moved tip reports the race after one fetch, and a seco assert.equal(w.remoteTip(), again); }); -// dewey-0864 R1: the race fetch takes sync's guard. A sync holds it (its fetch is a 3 s sleep, started -// only once the guard is taken), so the push's fetch refuses busy and the mirror's ref stays put. +// dewey-0864 R1: the race fetch takes sync's guard. A sync holds it: its fetch is a git alias that +// touches a marker, then waits for a release file. The push starts only once the marker exists and +// the release comes only after the refusal, so no step depends on timing (dewey-0869). test('C2-03b race fetch: while a sync of the mirror runs, the race refuses library-sync-busy', async t => { const w = await writeWorld(t); const moved = w.push({ 'Inbox Note.md': 'she wrote more\n' }); const before = git(w.mirror(), 'rev-parse', 'refs/remotes/library/main'); - let inside; - const held = new Promise(resolve => { inside = resolve; }); + const mark = join(w.root, 'hold.mark'), release = join(w.root, 'hold.release'); + const hold = '!f() { touch "$LIB_HOLD_MARK"; i=0; while [ ! -e "$LIB_HOLD_RELEASE" ] && [ $i -lt 1200 ]; do sleep 0.05; i=$((i+1)); done; }; f'; const slow = (kind, url, opts) => { const real = w.command(kind, url, opts); - inside(); - return { argv: ['-c', 'alias.hold=!sleep 3', 'hold'], env: real.env }; + return { argv: ['-c', 'alias.hold=' + hold, 'hold'], env: { ...real.env, LIB_HOLD_MARK: mark, LIB_HOLD_RELEASE: release } }; }; const syncing = sync(w.context, { slot: w.slot, command: slow }); - await held; + t.after(() => { try { writeFileSync(release, ''); } catch {} }); + const end = Date.now() + 30000; + while (!existsSync(mark) && Date.now() < end) await new Promise(r => setTimeout(r, 10)); + assert.ok(existsSync(mark), 'the sync is inside its fetch, holding the guard'); await assert.rejects(w.write({ commit: w.child(w.commit) }), { code: 'library-sync-busy' }); assert.equal(w.remoteTip(), moved, 'her commit stands'); + writeFileSync(release, ''); await syncing.catch(() => {}); assert.equal(git(w.mirror(), 'rev-parse', 'refs/remotes/library/main'), before, 'the refused race fetched nothing'); assert.deepEqual(await w.write({ commit: w.child(w.commit) }), { pushed: false, raced: true, tip: moved }, 'free again afterwards');