如何在执行`alembic upgrade head`时确保每个迁移文件执行后提交数据库?
如何在执行
alembic upgrade head时确保每个迁移文件执行后提交数据库? 我太懂你这种憋屈感了——更新ENUM类型时,因为迁移文件之间没提交,新枚举值死活用不了,被迫分两次跑alembic upgrade +1和alembic upgrade head,实在是麻烦。下面给你几个靠谱的解决办法:
1. 最简单:修改Alembic配置,开启单迁移事务
直接改你的alembic.ini配置文件,添加或者找到下面这个配置项并设置为true:
transaction_per_migration = true
这个配置的作用是让Alembic为每个迁移文件单独创建一个事务,执行完一个迁移就自动提交事务,再去执行下一个。这样你直接跑alembic upgrade head,每个迁移的变更都会被及时提交,ENUM的新值自然就能在后续迁移里正常用了,完全不用手动拆分执行步骤。
2. 迁移文件内手动提交(适合单文件内有ENUM更新+依赖操作的场景)
如果你不想改全局配置,或者某个迁移文件里同时包含了ENUM更新和依赖新值的操作,那可以在迁移文件里手动提交变更。比如:
from alembic import op import sqlalchemy as sa from sqlalchemy.dialects.postgresql import ENUM # 第一步:更新ENUM类型 new_my_enum = ENUM('EXISTING_VALUE', 'NEW_VALUE_1', 'NEW_VALUE_2', name='my_enum', create_type=False) new_my_enum.create(op.get_bind(), checkfirst=False) # 手动提交当前变更,让数据库识别新的ENUM值 op.get_bind().commit() # 第二步:执行依赖新ENUM值的操作,比如修改列类型或者插入数据 op.alter_column('my_table', 'status_column', type_=new_my_enum)
这种方式能在同一个迁移文件里拆分提交,避免因为事务未提交导致的新值无法识别问题。
3. 自定义脚本批量执行单个迁移并提交
如果上面两种方法都不符合你的需求,还可以写个简单的Python脚本,遍历所有待执行的迁移,逐个执行并手动提交:
from alembic.config import Config from alembic import command from alembic.script import ScriptDirectory from sqlalchemy import create_engine # 加载Alembic配置 alembic_cfg = Config("alembic.ini") script = ScriptDirectory.from_config(alembic_cfg) # 获取当前数据库版本和目标版本(head) current_rev = command.current(alembic_cfg, verbose=False).strip() target_rev = "head" # 获取需要执行的迁移列表,按执行顺序排列 revs = list(script.walk_revisions(current_rev, target_rev)) revs.reverse() # 逐个执行迁移并提交 for rev in revs: print(f"正在应用迁移: {rev.revision}") command.upgrade(alembic_cfg, rev.revision) # 获取数据库连接并提交 engine = create_engine(alembic_cfg.get_main_option("sqlalchemy.url")) with engine.connect() as conn: conn.commit()
运行这个脚本就会逐个执行每个迁移文件,每执行完一个就提交一次,完全模拟你手动跑两次命令的效果,但不用每次都手动操作。
内容来源于stack exchange
相关产品推荐
相关产品推荐

