Database migrations are where AI-assisted development gets genuinely risky. A code change that breaks a component gets caught in review or by a failing test. A migration that drops a column, rewrites a type, or backfills a billion rows touches production data that cannot be un-dropped. When you hand that work to Claude Code, the payoff is real, but so is the blast radius if you skip the guardrails.
At Automata AI in Sydney we run Claude Code against client schemas every week. This is the set of safety patterns we use so that speed never comes at the cost of a data-loss incident. None of it is exotic. It is disciplined engineering applied to an assistant that is fast enough to make a mistake before you have finished reading the diff.
Why migrations need their own rules
Claude Code is strong at writing migration files. It reads your schema, understands the intent, and produces up and down scripts that usually run first time. The problem is not the code it writes. The problem is that a migration is a one-way door in a way that most application code is not.
A single careless ALTER TABLE on a large production table can lock writes for minutes, time out your API, and cascade into a customer-facing outage. For a mid-sized Australian business, an hour of downtime during trading can cost well past $45,000 once you count lost transactions, support load, and the goodwill hit. Under the Privacy Act, an accidental exposure or loss of personal data during a botched migration can also become a notifiable breach. So the assistant needs tighter rails here than anywhere else in the codebase.
The core safety patterns
These are the patterns we make non-negotiable before Claude Code touches a schema. Treat them as a checklist, not a suggestion.
Always require a reversible down migration. If Claude writes an up script, it writes the matching down script in the same change, and you test the rollback locally before anything reaches staging.
Separate schema changes from data backfills. A migration that adds a nullable column is safe and instant. A migration that populates that column across ten million rows is a batched job that runs separately, with its own throttle and progress log.
Ban destructive operations in the same deploy that stops using them. Drop a column in a later release, never in the one that removes the code reading it. This keeps a clean rollback path if the deploy fails.
Force additive-first changes. New column, new table, new index built concurrently. Renames become add-plus-copy-plus-drop across multiple deploys, not a single risky rename.
Demand an explicit lock and timing note. Claude must state which locks the migration takes and the expected duration on a table of production size, so you can decide whether it runs in a maintenance window.
The point of writing these down is that Claude Code follows explicit instructions far better than it guesses at your risk tolerance. Put the rules in a project file it reads on every run, and the assistant stops proposing the fast-but-dangerous version.
Give Claude the context it needs to be safe
Most dangerous migrations come from missing context, not bad reasoning. If Claude Code does not know that your orders table has 40 million rows, it will happily suggest an index build that locks the table. Tell it the shape of production up front.
Row counts and rough table sizes for the tables in scope, so the assistant can reason about lock duration.
Which database engine and version you run, because safe patterns for Postgres differ from MySQL, and concurrent index builds are version-dependent.
Your read and write traffic pattern, so it knows whether a maintenance window is realistic or whether the change has to be fully online.
The migration tool and conventions you already use, so it produces files that match your existing runner rather than inventing a new approach.
A short MIGRATIONS.md in the repo that captures these facts is the single highest-return thing you can add. Claude Code reads it, and the quality of every migration it proposes goes up sharply.
Keep a human at the gate
Automation should end at the point where data is irreversibly changed. We let Claude Code write the migration, run it against a local copy, and open the pull request. A person reviews the up and down scripts, confirms the rollback works on a production-sized snapshot, and only then approves the deploy.
This is not distrust of the tool. It is the same principle any Sydney or Melbourne engineering team applies to production access. The assistant removes the tedious drafting work, which is exactly where its speed helps. The final go or no-go on touching customer data stays with an accountable engineer who can be named in an incident review.
We also keep a tested backup and a rehearsed restore path before any migration that changes existing data. Claude Code can write the restore runbook too, but you verify it by actually restoring into a scratch database, not by reading the steps and nodding.
A workflow that holds up
Put together, our standard loop looks like this. Claude reads the project rules and schema context. It proposes the migration as additive-first, reversible, with schema and backfill split apart. It runs the change locally and shows the timing and locks. A human reviews, tests the down path on a realistic snapshot, and approves. The deploy runs in the agreed window with the backfill throttled and logged.
That sequence is slower than letting the assistant push a migration straight to production. It is also the difference between a team that ships schema changes daily without drama and one that is one bad afternoon away from a Privacy Act notification. The safety patterns are cheap. The incident they prevent is not.
If you want help setting up Claude Code with migration guardrails that fit your stack and your risk profile, book a short call with us and we will walk through your schema and your deploy process together.



