Blog · TypeScript
What LockSmith checks before a migration ships
A migration can look harmless in a diff and still freeze production. Here's what LockSmith looks for, how it proves the lock in a real Postgres engine, and what it deliberately doesn't claim.
Migrations go through the same pull-request review as application code, but their risk doesn't show up in a diff. A one-line change can block every write to a table for as long as an index takes to build. I built LockSmith solo for the IBM Bob 2.0 Hackathon on lablab.ai to catch that before the deploy, not during it.
This post walks through what it checks, in the order it checks it.
1. The statements that take the wrong lock
LockSmith parses the SQL and runs twelve deterministic rules, LS001 to LS012, over it. Between them they cover:
CREATE INDEXwithoutCONCURRENTLY. It holds a ShareLock that blocks writes for the whole build.CONCURRENTLYinside a transaction. Postgres won't allow it, so a migration that looks safe fails outright.ALTER COLUMN … TYPE. It takes an AccessExclusiveLock and usually rewrites the table.- Adding
NOT NULL, and adding columns with volatile defaults, which can force a full-table scan or rewrite. - Validated foreign keys and check constraints added in one step, which scan the table under lock instead of being added
NOT VALIDand validated later. - Renames and drops still referenced by application code. A rename is instant in the database, but it breaks every running app instance still using the old name.
- Heavy DDL without
lock_timeout. It can queue behind one slow query and freeze everything behind it. - Un-batched backfills, where one huge
UPDATEholds row locks and bloats the table.
None of these needs a model to spot. They're rules, and in LockSmith's design the rules decide what's risky.
2. Proof, not just a rule name
A warning with a rule ID starts an argument in review. A measured lock ends one.
So every statement is replayed in PGlite, which is PostgreSQL compiled to WASM and run in-process. LockSmith reads pg_locks to see the lock the statement actually took, and compares relfilenode before and after to detect whether the table was rewritten. LockSmith never connects to your real database.
There's one honest gap. CREATE INDEX CONCURRENTLY can't run inside the probe's transaction, so its lock is marked inferred in the UI rather than presented as measured. I'd rather show that label than pretend.
3. How long it would hurt
A lock only matters for as long as it's held. LockSmith takes the production table sizes you declare and turns each lock into something like "about N seconds, about M writes blocked".
Those numbers are estimates. They come from declared row counts and fixed throughput constants, not from timing your hardware, and the report says so.
4. The rewrite, and the re-check
Flagged migrations go to IBM Bob, through a custom mode called Migration Surgeon, a lock reference and a lock-audit skill that ship in the repo. Bob rewrites each flagged migration in its own subagent into expand, backfill and contract steps. It updates dependent application code too, for example adding dual-writes for a rename, and it leaves unflagged files alone.
Then Bob's output goes back through the same engine. The CLI exits non-zero while any critical finding remains, so the gate in CI judges the AI's work by the same rules it applied to mine.
In the demo run, Bob withdrew its own column-drop step after noticing the app still wrote to that column. The gate would have caught it anyway, and that's the point of putting deterministic checks in front of and behind the model.
What the demo shows
The demo repository is a fictional shop app with 8 pending migrations. As written, the gate fails with a risk score of 100 and 14 findings. After Bob's rewrite it passes with 0 findings, and 6 dangerous migrations have become 13 ordered safe files. On 27 September 2026 the project had 61 of 61 tests passing, a clean typecheck and a successful production build.
In the interest of honest attribution: IBM Bob wrote most of the engine across six IDE tasks, including the rules, the probe, the mode and 53 of the tests, and I reviewed and re-ran each change. I wrote the spec, the fictional demo repository, the UI and the CLI output, using Claude Code as a coding assistant.
What it doesn't do yet
LockSmith covers PostgreSQL and plain SQL migration files only. The roadmap lists a GitHub Action wrapper, Prisma, Rails and Flyway adapters, importing real pg_stat table sizes, and MySQL online-DDL rules.
If you want the full write-up, with the architecture and the trade-offs, it's in the LockSmith case study. For more on how I use Postgres, see the PostgreSQL skill page. Teqprotech's custom web applications service lists LockSmith among its proof projects.
Work like this runs through Teqprotech · Custom Web Applications