这是迁移图出现分叉,需用makemigrations --merge生成合并迁移文件,并手动补全operations确保逻辑顺序正确,再通过sqlmigrate验证sql后执行migrate。

showmigrations 显示多个未应用的头节点怎么办
这说明迁移图已分叉,Django 不知道该先执行哪一个。运行 python manage.py showmigrations 后,如果某个 app 下出现两个或多个标记为 [ ] 的迁移文件(例如 0003_add_status 和 0003_rename_field),且它们都直接依赖同一个父迁移(如 0002_auto),就属于典型冲突。
此时不要手动删文件或清空 django_migrations 表——这会让团队其他人同步失败。
- 先确认是否真由 Git 合并引起:检查这两个
0003_*.py文件是否来自不同分支、编号相同但内容不同 - 若已合并进主干,且本地有冲突迁移,优先用
makemigrations --merge生成合并文件,而不是重命名再手工改 - 但注意:
--merge只解决“结构分叉”,不解决“逻辑冲突”——它生成的文件里operations = [],你得自己填
makemigrations --merge 生成的迁移文件为什么是空的
makemigrations --merge 的作用只是创建一个新迁移,把冲突的两个父节点写进 dependencies,它不会、也不能自动推断字段增删顺序或类型变更兼容性。
比如分支 A 删除了 name 字段,分支 B 把 name 的 max_length 从 50 改成 100,合并迁移必须明确写出 RemoveField 在前、还是 AlterField 在后,否则 migrate 执行时会报错。
- 打开生成的
0004_merge_*.py,检查dependencies是否包含两个冲突迁移,例如[('myapp', '0003_add_status'), ('myapp', '0003_rename_field')] - 手动补全
operations:逐条比对两个冲突迁移的operations列表,合并去重,注意顺序(删除操作不能放在修改之后) - 务必用
python manage.py sqlmigrate myapp 0004_merge_*预览 SQL,确认没有对同一字段重复ALTER TABLE
多人协作中怎么避免下次再冲突
根本问题不是 Git 合并失败,而是模型状态和迁移历史错位。常见诱因是:开发者在未提交迁移文件的情况下切分支,或多人基于同一旧迁移各自生成同名新迁移。
- 约定所有人在改
models.py后立刻运行makemigrations并提交迁移文件,不等 PR 合并后再补 - CI/CD 中跑迁移命令必须加
--noinput,否则--merge会卡在交互提示上 - 禁止手动编辑已提交的迁移文件(尤其是
dependencies或operations),哪怕只改个逗号——Django 会校验文件哈希 - 新成员拉代码后第一件事不是
migrate,而是先showmigrations看有没有悬空头节点
为什么不能用 --fake-initial 绕过冲突
--fake-initial 只在一种场景合法:项目已有数据库表结构,但尚未接入 Django 迁移系统。它会跳过 0001_initial.py 的执行,仅在 django_migrations 表中标记为已应用。
把它用在冲突场景,等于告诉 Django “别管这些迁移,我表自己心里有数”——但没人真心里有数。后果是后续迁移因 dependencies 断链而报 InconsistentMigrationHistory,且队友执行 migrate 时必然失败。
真正需要的是让所有人共享同一套线性迁移链,而不是靠 fake 掩盖不一致。
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!











