Django 迁移未检测到所有更改

Posted

技术标签:

【中文标题】Django 迁移未检测到所有更改【英文标题】:Django migrations not detecting all changes 【发布时间】:2017-08-22 22:47:08 【问题描述】:

我有以下型号。 BaseClass1BaseClass2 是模型使用的抽象模型。

在这种情况下,模型AdBreak 由视图集和序列化程序使用。 当我运行python manage.py makemigrations 时,会检测到AdBreak 模型的变化。未创建模型 AdBreakStatus

由于AdBreakStatusAdBreak 相关联,我也期待AdBreakStatus 的迁移。是不是我的理解错了?

编辑

在初始状态下,只有 AdBreak 和 BaseClass1 模型。添加了新状态、AdBreakStatus 和 BaseClass2 模型。 AdBreak 中的一些字段已移至 AdBreakStatus。

提前感谢您的帮助。

class BaseClass1(models.Model):
    class Meta:
        abstract=True
    timestamp = models.DateTimeField(auto_now_add=True)

class BaseClass2(models.Model):
    class Meta:
        abstract=True
    other_field = models.IntegerField()

class AdBreak(BaseClass1):
    class Meta:
        db_table = "ad_break"
    ad_break_id = models.AutoField(primary_key=True)
    ... # Other fields

class AdBreakStatus(BaseClass2):
    class Meta:
        db_table = "ad_break_status"
    ad_break = models.ForeignKey(AdBreak)
    ... # Other Fields

【问题讨论】:

数据库迁移将数据库从一种状态转换为另一种状态。您只向我们展示了一个状态;在无法回答之前不知道您的模型(或表格)的外观。 初始状态只有AdBreak和BaseClass1模型。添加了新状态、AdBreakStatus 和 BaseClass2 模型。 AdBreak 中的一些字段已移至 AdBreakStatus。 @Chris :如果我添加一个指向AdBreakStatus 的视图集,则会检测到迁移。还有其他方法吗? 【参考方案1】:

如果有人和我犯了同样的错误,就我而言,这是因为我添加的字段与现有属性具有相同的名称。因此,请确保该字段名称尚未使用。

【讨论】:

【参考方案2】:

我通过多种方式解决了它。

解决方案 1

有一个序列化器AdBreakSerializer 序列化模型AdBreak。 将AdBreakStatus 模型导入AdBreakSerializer 文件。 现在AdBreakStatus 模型被检测并迁移。

这种方法的问题是,没有使用导入,因此不会遵循标准。

解决方案 2

AdBreak 的同一个文件中写入AdBreakStatus 模型类。这也将解决问题。


发现/理解

makemigrations 脚本查找从urls.py 连接的模型。该脚本从urls.py 导航到所有视图集,然后是相应的序列化程序和模型。

所有需要迁移的模型都应该在这个遍历的路径中。 只有以这种方式遍历的模型才会被迁移。

【讨论】:

您的发现是正确的,但它们只是 Django 工作方式的副作用(事实上,直到添加了导入您的 urls.py 的 URL 系统检查,这才是正确的)。 Django 显式导入INSTALLED_APPS 中每个应用程序的models 子模块。如果要加载模型,请确保将其导入models.pymodels/__init__.py。这样,您就不会依赖任何可能在应用程序开发过程中发生变化的导入链。它还提供了一个方便的地方来在一个地方访问您的模型,即使它们是在多个文件中定义的。【参考方案3】:

先这样做:

python manage.py makemigrations 'your-app'
python manage.py migrate

如果上述方法未能检测到更改,请删除迁移文件夹,打开数据库并打开表 django_migrations。您将看到与您的应用关联的迁移列出,删除记录,现在执行 makemigrations 和迁移。

【讨论】:

此解决方案适用于应用程序处于测试阶段/初始开发阶段。不适合应用的后期阶段。【参考方案4】:

删除迁移文件夹和 sqlite 文件。然后运行

python manage.py makemigrations 'app_name'
python manage.py migrate

【讨论】:

此解决方案适用于应用程序处于测试阶段/初始开发阶段。不适合应用的后期阶段

以上是关于Django 迁移未检测到所有更改的主要内容,如果未能解决你的问题,请参考以下文章

Django 1.8:删除迁移文件夹后未检测到迁移

我不小心删除了 Django 中的迁移文件夹

运行显式创建表的迁移时未创建 Django 表。

Flask-Migrate 首次迁移时未检测到架构更改

Django 1.7 - 创建初始迁移

即使在运行迁移后,Django Programming 错误列也不存在