Django中的OnetoOne(primary_key = Tue)到ForeignKey

Posted

技术标签:

【中文标题】Django中的OnetoOne(primary_key = Tue)到ForeignKey【英文标题】:OnetoOne (primary_key=Tue) to ForeignKey in Django 【发布时间】:2020-09-07 19:46:34 【问题描述】:

我在模型中有一个具有 primary_key=True 的 OnetoOne 字段。 现在我想将其更改为 ForeignKey 但不能因为没有“id”。

从这里:

user = models.OneToOneField(User, primary_key=True, on_delete=models.CASCADE)

到这里:

user1 = models.ForeignKey(User, related_name='questionnaire', on_delete=models.CASCADE)

在迁移时显示这个:

您正在尝试在没有默认值的情况下向historyuserquestionnaire 添加不可为空的字段“id”;我们不能这样做(数据库需要一些东西来填充现有的行)。 请选择一个修复: 1) 现在提供一次性默认值(将在所有现有行上设置此列的空值) 2)退出,让我在models.py中添加一个默认值

那该怎么做呢? 谢谢!

【问题讨论】:

如果您尝试允许 null=True 之类的空值,或者将默认用户设置为 default= 不一样,因为主键是 True 所以这些对象没有 id 【参考方案1】:

问题是您试图删除主键,但 Django 会添加一个名为“id”的新主键。这是不可为空且唯一的,因此您不能真正提供一次性默认值。

最简单的解决方案是创建一个新模型并在 SQL 迁移中复制您的表,使用旧的 user_id 填充 id 字段。请务必重置您的表格顺序以避免冲突。

【讨论】:

不想这样做,这就是我发布此内容的原因 似乎没有其他选项可以执行此操作 谢谢! 无论你如何处理,不要忘记在你的数据库中重新设置序列以避免冲突。如果您想尝试另一种方式,您将不得不使用SeparateDatabaseAndState 操作来添加 id 字段状态,并且可能只需将数据库中的 user_id 列复制到 id。【参考方案2】:

Django 模型有一个默认的 ID 属性。由于您更改了模型,以前的数据记录现在与您的新列属性冲突,因为在添加以前的记录时,没有 ForeignKey。请记住,在您的外键中,不允许使用空值。您的解决方案有多个修复程序。一步一步地执行这些步骤,看看是什么解决了您的错误。

删除您的迁移文件并再次运行迁移

在你的外键中设置 NULL=True

删除表之前的记录以解决冲突,这样当你运行迁移时,它会添加一个默认值 id 本身

除了删除之外,您还可以尝试像这样直接更改迁移文件

https://***.com/a/29074241/11979793

【讨论】:

问题不在于ForeignKey字段的迁移,问题在于删除OnetoOne字段,因为primary_key为True 这个帖子有帮助吗? ***.com/questions/2055784/… 没那么重要,反正我已经解决了这个问题,方法是用我想要的字段创建一个新模型并传输数据。【参考方案3】:

只需删除您以前的迁移

e.g 

    migrations:
          |
          |- 001.initail.py
          |- 002.examplefiles.py

你只需要删除你最近的迁移和

运行命令

python3 manage.py makemigrations
python3 manage.py migrate

【讨论】:

不,这没有帮助

以上是关于Django中的OnetoOne(primary_key = Tue)到ForeignKey的主要内容,如果未能解决你的问题,请参考以下文章

django OneToOne 反向访问

附加“_id”的OneToOne字段上的Django过滤器并失败

Django Admin:如何在 oneToOne 关系中的两个模型中显示带有 list_display 的字段值?

Django 中的 OneToOne、ManyToMany 和 ForeignKey 字段有啥区别?

检查 Django 中是不是存在 OneToOne 关系

Django 1.11 admin:创建 OneToOne 关系,它是 admin 中的对象