Build Log
Game Builder's Parent Approval Gate Gets Real Persistence, and Witness Gets Its First Real Test
August 25, 2026
Replaced Game Builder's file-backed, race-prone parent-approval-gate store with real Neon/Drizzle persistence and a genuinely atomic concurrency fix, while running the ForgeKit Strategic Validation Sprint H2 protocol (Witness at the commitment boundary) for the first time on real, non-OS-diagnostic product work.
Timeline
What shipped
experiments/game-builder/lib/db/schema.ts — new publish_requests and audit_log Postgres tables, replacing publish-requests.json and audit-log.jsonl
experiments/game-builder/lib/db/index.ts — createDb wiring, same pattern as Hearth/Forge
experiments/game-builder/lib/approval-gate/store.ts — rewritten for real DB access; decideAtomically() replaces the old read-then-write decideRequest logic with one atomic conditional UPDATE
experiments/game-builder/lib/approval-gate/service.ts — decideRequest() now distinguishes 'lost the race' from 'not found' honestly via decideAtomically()'s null return, not a thrown generic error
experiments/game-builder/lib/approval-gate/service.test.ts — real-DB concurrency regression test (Promise.allSettled, no vi.mock), verified to fail honestly without a live DB, not yet run against one
experiments/game-builder/drizzle.config.ts, package.json (added @neondatabase/serverless, drizzle-orm, drizzle-kit, forgekit-core, forgekit-testing, dotenv, tsx; added db:push and test scripts)
experiments/game-builder/docs/parent-approval-gate.md §7 — items 1 and 3 marked RESOLVED with what was verified and what remains a real deployment-time gap (no live Neon DB provisioned yet)