agent ran alembic with the dev alembic.ini against the production database
Recovery and prevention for running alembic with the dev alembic.ini against the production database: assessing what the dev config changed, and separating configs per environment. Use when the wrong ini file targeted the wrong database or applied dev settings to prod. Not for correct-config migrations that failed.
TL;DR
The dev ini pointed at (or configured for) the wrong database, so a dev-configured alembic ran against production. Assess what ran and with what settings, then separate configs per environment: one ini per environment (or one ini reading the URL from the environment), a wrapper that selects by explicit --env flag, and a guard that refuses dev-configured runs against production hosts.
The query
agent ran alembic with the dev alembic.ini against the production databaseUse this when
- Alembic ran with dev alembic.ini against production
- Wrong ini file targeted the wrong database
- Need per-environment alembic configs
- An agent used the dev config on prod
Not for
- The right config failing on prod (fix the migration)
- A dev ini used on a dev database (that is its job)
- Connection-string confusion without ini involvement (guard the URL directly)
Steps
1. Assess what ran and under what settings
Read the dev ini: which sqlalchemy.url did it resolve to, and what settings differ from prod (echo, pool sizes, transaction settings)? Check the state table on the affected database to see which revisions applied.
Expected output: the exact database hit, the revisions applied, and any dev-only settings (like verbose echo or aggressive pooling) that touched prod.
2. Contain and reconcile
If unexpected revisions applied to prod, reconcile the schema and the history (inventory, hand-apply or stamp, as with any out-of-place migration). Rotate any credentials the dev config exposed. Expected output: prod's schema and history are consistent and deliberate again.
3. Separate configs per environment
Create alembic.prod.ini (and staging), or keep one ini that reads the URL from the environment and nothing else. No ini file should contain a production URL as a default a dev command can pick up accidentally.
Expected output: there is no single file that a bare alembic command can load and hit prod with.
4. Add the env-selecting wrapper
The agent runs migrations through a wrapper requiring --env, which selects the ini and prints the resolved target for confirmation. The wrapper refuses --env prod without an additional explicit confirmation flag.
Expected output: running alembic "the normal way" cannot reach prod; reaching prod requires two deliberate flags.
5. Make the dev ini unable to reach prod structurally
The dev ini's URL should resolve to a local database only (YOUR_HOST, or a socket). If the dev config cannot address prod at the network level, the wrong-ini mistake becomes a connection error, not an incident.
Expected output: the entire class of mistake degrades to "connection refused".
Tool compatibility
alembic 1.x. The per-environment config pattern applies to any ini-based tool.
Variant phrasings
alembic dev ini against production
Steps 1 and 2: assess what ran, reconcile prod.
per-environment alembic config
Step 3: one ini per environment, no prod URL as any default.
prevent alembic hitting wrong database
Steps 4 and 5: env-selecting wrapper plus a dev ini that cannot route to prod.
Why it happens
Alembic resolves its database from the ini file, and a bare alembic command loads alembic.ini from the current directory: whatever that file says is the target. When the dev ini is the default and it can address prod (via an env var someone exported, or a URL someone pasted), the tool does exactly what it was configured to do. The bug is a configuration that makes the wrong target reachable by default.
Edge cases
- Env-var-driven URLs are the usual vector: the ini reads sqlalchemy.url from DATABASE_URL, and the agent's shell had prod's. Fix the shell hygiene too, not just the ini.
- A wrapper the agent can bypass with an env var is decoration: the prod confirmation must be a separate explicit flag.
- Audit other ini-driven tools in the agent's reach (pytest configs, deploy scripts): the same default-config hazard usually exists in more than one place.
Provenance
Resolved from the public thread: https://vectle.com/posts/pst__iZwFiI1B4Z7LA4dYS01tQ