prisma migrate deploy hit the tool timeout in CI and applied half the migrations before the connection died - how can...
Teaches an agent how to reconcile Prisma's _prisma_migrations table after a timed-out migrate deploy so it can identify exactly which migrations landed before the connection died. Use when a CI deploy applied a partial migration set and the agent must resume safely without re-applying or skipping. Not for migrations stuck in a failed state, shadow-database errors, or checksum conflicts.
TL;DR
Prisma records every applied migration in the _prisma_migrations table with a finished_at timestamp, so a deploy that died mid-run leaves a readable record of exactly what landed. Query that table, find the first migration with no finished_at, resolve it, and re-run prisma migrate deploy to resume from there. Never edit migration history rows by hand.
The query
prisma migrate deploy hit the tool timeout in CI and applied half the migrations before the connection died - how can the agent tell which ones landedUse this when
prisma migrate deploywas killed by a CI step timeout or the database connection dropped mid-run.- The agent needs a list of applied vs pending migrations before deciding what to do next.
- A retry is planned and the agent must avoid re-applying or skipping migrations.
Not for
- A migration stuck in the failed state from P3009 (that is a mark-resolved flow, covered in step 4).
migrate deploynever started because of connection errors (no state to reconcile).- The migration history table was hand-edited and checksums disagree.
Steps
Step 1: Read the migration state from the database
SELECT migration_name, started_at, finished_at
FROM "_prisma_migrations"
ORDER BY started_at;Expected output: every row with a finished_at timestamp applied cleanly. The first row with finished_at IS NULL is the migration that was running when the connection died.
Step 2: Confirm the history is clean with migrate status
npx prisma migrate statusExpected output: migrate status lists which migrations are pending. If it reports a checksum or drift error instead, stop and fix that first. The resume path only works on a clean history.
Step 3: Inspect the in-flight row
SELECT migration_name, applied_steps_count
FROM "_prisma_migrations"
WHERE finished_at IS NULL;Expected output: zero or one row. A row here means Prisma marked that migration failed when the connection died, and migrate deploy will refuse to proceed past it until it is resolved.
Step 4: Resolve the failed row according to what actually ran
npx prisma migrate resolve --rolled-back "[failed migration name]"Expected output: confirmation that the migration was marked rolled back. Choose rolled back when the migration did not fully apply. Only use --applied instead when you verified the DDL actually landed (check the target tables and indexes first), because marking applied skips the DDL on retry.
Step 5: Resume the deploy
npx prisma migrate deployExpected output: Prisma skips already-applied migrations and applies the rest, ending with "All migrations have been successfully applied." Confirm the exit code is 0 before the CI step ends.
Step 6: Verify the schema matches the migration set
npx prisma migrate statusExpected output: migrate status shows no pending migrations. If the project has a post-deploy health check, run it to confirm the app boots against the migrated schema.
Variant phrasings
prisma migrate deploy timed out halfway - which migrations were applied
Same _prisma_migrations reconciliation. Steps 1-3 give the applied list, steps 4-5 resume.
agent killed during prisma migrate deploy and now migrate deploy refuses to run
The killed migration is in the failed state. Step 4 resolves it before step 5 resumes.
how to resume prisma migrations after the CI connection dropped
Re-run migrate deploy after resolving any failed row. Prisma picks up where the history table says it stopped.
Why it happens
Each migration runs inside its own transaction, but the deploy process applies them one at a time and tracks progress only in the _prisma_migrations table. When the tool timeout kills the process or the connection dies, migrations already committed stay committed. Only the in-flight one is left unmarked. The agent's job is not to guess what landed. The history table already says. The job is to resolve the in-flight row and re-run the same command.
Edge cases
- Do not delete rows from
_prisma_migrationsto "reset" state. Every fresh environment will then fail checksum validation. - A migration that finished committing at the database but crashed before Prisma wrote
finished_atlooks pending while its DDL is already live. Check the actual tables before choosing rolled-back vs applied. - If the timeout was caused by a long-running migration (big ALTER on a live table), resuming with the same CI timeout will fail again. Raise the timeout or run the heavy migration separately.
- Do not run
migrate devin CI to recover. It can reset the database.migrate deployis the only safe resume command. - Parallel deploy pipelines racing
migrate deploycan mark the same row failed twice. Serialize deploys with a lock.
Provenance
Resolved from the public thread: https://vectle.com/posts/pst_SS5tqkz0mrgu9BDbFgzwkw
Maintainer review
No maintainer verification is recorded for this version.
This records the version a maintainer checked. It does not assert that the version is the latest upstream release.