我计划在现有 Django 项目中重命名多个模型,其中有许多其他模型与我要重命名的模型具有外键关系。我相当肯定这将需要多次迁移,但我不确定确切的过程。
假设我从名为 Django 应用程序中的以下模型开始myapp:
myapp
class Foo(models.Model): name = models.CharField(unique=True, max_length=32) description = models.TextField(null=True, blank=True) class AnotherModel(models.Model): foo = models.ForeignKey(Foo) is_awesome = models.BooleanField() class YetAnotherModel(models.Model): foo = models.ForeignKey(Foo) is_ridonkulous = models.BooleanField()
我想重命名Foo模型,因为该名称实际上没有意义,并且会导致代码混乱,并且Bar会使名称更清晰。
Foo
Bar
根据我在 Django 开发文档中阅读的内容,我假设以下迁移策略:
修改models.py:
models.py
class Bar(models.Model): # <-- changed model name name = models.CharField(unique=True, max_length=32) description = models.TextField(null=True, blank=True) class AnotherModel(models.Model): foo = models.ForeignKey(Bar) # <-- changed relation, but not field name is_awesome = models.BooleanField() class YetAnotherModel(models.Model): foo = models.ForeignKey(Bar) # <-- changed relation, but not field name is_ridonkulous = models.BooleanField()
请注意,AnotherModel字段名称foo不会更改,但关系会更新为Bar模型。我的理由是我不应该一次更改太多,如果我将此字段名称更改为bar我将冒丢失该列中的数据的风险。
AnotherModel
foo
bar
创建一个空迁移:
python manage.py makemigrations --empty myapp
编辑Migration步骤 2 中创建的迁移文件中的类,将操作添加RenameModel到操作列表中:
Migration
RenameModel
class Migration(migrations.Migration): dependencies = [ ('myapp', '0001_initial'), ] operations = [ migrations.RenameModel('Foo', 'Bar') ]
应用迁移:
python manage.py migrate
编辑相关字段名称models.py:
class Bar(models.Model): name = models.CharField(unique=True, max_length=32) description = models.TextField(null=True, blank=True) class AnotherModel(models.Model): bar = models.ForeignKey(Bar) # <-- changed field name is_awesome = models.BooleanField() class YetAnotherModel(models.Model): bar = models.ForeignKey(Bar) # <-- changed field name is_ridonkulous = models.BooleanField()
创建另一个空迁移:
编辑Migration在步骤 6 中创建的迁移文件中的类,将RenameField任何相关字段名称的操作添加到操作列表中:
RenameField
class Migration(migrations.Migration): dependencies = [ ('myapp', '0002_rename_fields'), # <-- is this okay? ] operations = [ migrations.RenameField('AnotherModel', 'foo', 'bar'), migrations.RenameField('YetAnotherModel', 'foo', 'bar') ]
应用第二次迁移:
除了更新其余代码(视图、表单等)以反映新的变量名称之外,这基本上是新迁移功能的工作方式吗?
此外,这似乎有很多步骤。迁移操作可以以某种方式压缩吗?
谢谢!
因此,当我尝试此操作时,您似乎可以压缩第 3 - 7 步:
class Migration(migrations.Migration): dependencies = [ ('myapp', '0001_initial'), ] operations = [ migrations.RenameModel('Foo', 'Bar'), migrations.RenameField('AnotherModel', 'foo', 'bar'), migrations.RenameField('YetAnotherModel', 'foo', 'bar') ]
如果您不更新导入它的名称,例如 admin.py 甚至更旧的迁移文件 (!),您可能会遇到一些错误。
更新 :正如ceasaro提到的,较新版本的 Django 通常能够检测并询问模型是否被重命名。所以先尝试manage.py makemigrations,然后检查迁移文件。
manage.py makemigrations