diff --git a/agents/bubba/work/queue-288/BUILD.md b/agents/bubba/work/queue-288/BUILD.md index f71f02059..a7c3c8b12 100644 --- a/agents/bubba/work/queue-288/BUILD.md +++ b/agents/bubba/work/queue-288/BUILD.md @@ -435,3 +435,16 @@ Whole write.test.mjs now rc0,12/12,0 skipped/cancelled. Source-only fix in owned Logs remain /mnt/storage/scratch/bubba-row288/gate-r3/ (write-fixed through write-fixed4). Sage4398 authorizes this fix and requires committed new candidate + driver restart from first whole file. Focused green is not the complete gate; remaining acceptance pending. + +## 2026-10-25 new broker-fixture RED/GREEN, driver restart pending + +Candidate7932c979a driver first library file rc0,12/12; second own bus library-write rc1, +0/14 (fixture FK and undefined dataRoot). Own fixture lacked gitea_users parent; insert +with valid16-hex nonce, consistent with landed credential tests. First attempted fixture +nonce was invalid and INSERT OR IGNORE hid it; corrected nonce, no product/schema changes. +Every bare.dataRoot reference was undefined: use bare.context.dataRoot. After these fixes, +whole file rc1,13/14, last assertion assumed lines were strings; query returns [line,text]. +Corrected this row's new assertion to exact [1,'new served text']; whole file rc0,14/14, +0 skipped/cancelled. Intermediate logs bus-fixture-fixed{,2,3} under gate-r4 retained. +Only owned new bus/tests/library-write.test.mjs changes (+14/-12); no pre288 test changed +or failed. Commit this fixture correction, then restart all289 whole files from the start. diff --git a/packages/bus/tests/library-write.test.mjs b/packages/bus/tests/library-write.test.mjs index 1a62f055f..c3a7343bf 100644 --- a/packages/bus/tests/library-write.test.mjs +++ b/packages/bus/tests/library-write.test.mjs @@ -48,6 +48,8 @@ function world(t, options = {}) { } const grant = (project = 'books') => { const decision = grantDecision(store, { business: 'acme', grant: { method: 'gitea', agent: 'bean', target: { projects: [project] }, rotateBy: '2099-01-01' } }); + store.run('INSERT OR IGNORE INTO gitea_users(business,agent,user,id,nonce,decision) VALUES(?,?,?,?,?,?)', + 'acme', 'bean', 'bean', 7, '0123456789abcdef', decision); store.run('INSERT OR REPLACE INTO gitea_grants(business,agent,user,token_id,token_name,projects,rotate_by,decision) VALUES(?,?,?,?,?,?,?,?)', 'acme', 'bean', 'bean', 7, 'fixture', JSON.stringify([project]), '2099-01-01', decision); }; @@ -124,7 +126,7 @@ test('C2-02 transport: human library.file.save exceeds 64 KiB; agent write remai test('C2-02 M12 through broker: every refusal preserves remote, served and all mirror refs', async t => { const bare = await bareWorld(t), f = world(t, { projects: bare.context.business.projects }); - f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.dataRoot }, + f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.context.dataRoot }, { ...options, credential: { ...options.credential, file: bare.file }, command: bare.command }); for (const path of ['Book One/Chapters/Chapter 01.md', 'Inbox Note.md', 'Book One/Playground/What If.md', 'Book One/Notes/X.canvas', 'Book One/Notes/X.base', 'Book One/Notes/X.png', 'Second World/Chapters/01.md', @@ -143,11 +145,11 @@ test('C2-02 M12 through broker: every refusal preserves remote, served and all m test('C2-02 broker + bare: exact write/delete notices, then human revert with revoked seat grant', async t => { const bare = await bareWorld(t), f = world(t, { projects: bare.context.business.projects }); - f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.dataRoot }, + f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.context.dataRoot }, { ...options, credential: { ...options.credential, file: bare.file }, command: bare.command }); - f.library.revert = context => revertLibraryCommit({ ...context, dataRoot: bare.dataRoot }, + f.library.revert = context => revertLibraryCommit({ ...context, dataRoot: bare.context.dataRoot }, { credential: { ...bare.credential, kind: 'human' }, command: bare.command }); - f.library.saveFile = context => saveLibraryFile({ ...context, dataRoot: bare.dataRoot }, + f.library.saveFile = context => saveLibraryFile({ ...context, dataRoot: bare.context.dataRoot }, { credential: { ...bare.credential, kind: 'human' }, command: bare.command }); const base = git(bare.mirror, 'rev-parse', `served:${PATH}`); const saved = await f.call('bean', 'library.doc.write', { ...args(), base }); @@ -190,7 +192,7 @@ test('C2-02 E2: held grant during fetch refuses at beforePush and preserves ever if (kind === 'fetch') f.held.add('bean'); return bare.command(kind, url, options); }; - f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.dataRoot }, + f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.context.dataRoot }, { ...options, credential: { ...options.credential, file: bare.file }, command }); await assert.rejects(f.call('bean', 'library.doc.write', { ...args(), base: git(bare.mirror, 'rev-parse', `served:${PATH}`) }), { code: 'library-write-no-grant' }); @@ -234,7 +236,7 @@ test('C2-02 F2/E6 runtime: human saves/reverts use editor.user; no login never u const initial = (await bare.state()).lastFetch; const business = { ...bare.context.business, human: 'jason', roles: { coder: { authority: { withinRole: [], crossRole: [] } } }, arbiters: { technical: 'coder', delivery: 'coder' } }; - const runtime = await startBroker({ dataRoot: bare.dataRoot, businesses: { acme: business }, + const runtime = await startBroker({ dataRoot: bare.context.dataRoot, businesses: { acme: business }, librarySync: { configDir, command, intervalMs: 60000 } }); try { const human = runtime.broker.bindHuman({ business: 'acme', human: 'jason', via: 'cli', outsideAgent: true }); @@ -273,7 +275,7 @@ test('C2-02 E4: post-push publication failure stores the exact notice and return if (kind === 'push') writeFileSync(state, 'invalid state\n'); return bare.command(kind, url, options); }; - f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.dataRoot }, + f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.context.dataRoot }, { ...options, credential: { ...options.credential, file: bare.file }, command }); try { await assert.rejects(f.call('bean', 'library.doc.write', { ...args(), base: git(bare.mirror, 'rev-parse', `served:${PATH}`) }), @@ -295,7 +297,7 @@ test('C2-02 E4: post-push publication failure stores the exact notice and return test('C2-02 mos-1520: failed notice insert logs metadata and returns outcome-unknown even if refusal evidence fails', async t => { const bare = await bareWorld(t), f = world(t, { projects: bare.context.business.projects }); const previous = await servedCommit(bare.mirror), head = bare.remoteHead(); - f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.dataRoot }, + f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.context.dataRoot }, { ...options, credential: { ...options.credential, file: bare.file }, command: bare.command }); f.store.run(`CREATE TEMP TRIGGER fail_library_notice BEFORE INSERT ON messages WHEN NEW.from_role='bean' BEGIN SELECT RAISE(ABORT, 'fixture store failure'); END;`); @@ -313,9 +315,9 @@ test('C2-02 mos-1520: failed notice insert logs metadata and returns outcome-unk test('C2-02 + C2-05c: broker get blob feeds write/delete and new served lookups immediately', async t => { const bare = await bareWorld(t), f = world(t, { projects: bare.context.business.projects }); - f.library.lookup = createLibraryLookup({ dataRoot: bare.dataRoot, - sync: context => sync({ ...context, dataRoot: bare.dataRoot }, { credential: bare.credential, command: bare.command }) }); - f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.dataRoot }, + f.library.lookup = createLibraryLookup({ dataRoot: bare.context.dataRoot, + sync: context => sync({ ...context, dataRoot: bare.context.dataRoot }, { credential: bare.credential, command: bare.command }) }); + f.library.writeDoc = (context, options) => writeLibraryDoc({ ...context, dataRoot: bare.context.dataRoot }, { ...options, credential: { ...options.credential, file: bare.file }, command: bare.command }); const query = { universe: 'harbor', path: PATH, scope: 'supporting' }; const before = await f.call('bean', 'library.get', query); @@ -325,7 +327,7 @@ test('C2-02 + C2-05c: broker get blob feeds write/delete and new served lookups assert.equal(after.commit, saved.commit); assert.equal(after.blob, git(bare.mirror, 'rev-parse', `${saved.commit}:${PATH}`)); assert.notEqual(after.blob, before.blob); - assert.ok(after.lines.includes('new served text')); + assert.deepEqual(after.lines[0], [1, 'new served text']); assert.equal(await f.call('bean', 'library.get', { universe: 'harbor', path: PATH }), null); await f.call('bean', 'library.doc.delete', { universe: 'harbor', path: PATH, base: after.blob }); assert.equal(await f.call('bean', 'library.get', query), null);