在 ForeignKey 上设置 unique=True 与使用 OneToOneField 的效果相同

Posted

技术标签:

【中文标题】在 ForeignKey 上设置 unique=True 与使用 OneToOneField 的效果相同【英文标题】:Setting unique=True on a ForeignKey has the same effect as using a OneToOneField 【发布时间】:2015-09-04 02:03:44 【问题描述】:

我最近从 1.7 切换到 Django 1.8.2,但遇到了一些问题,例如在我的一个模型中:

class Author(models.Model):
    author = models.ForeignKey(UserProfile, blank=False, primary_key=True)
    timestamp = models.DateTimeField(auto_now_add=True)

但是当我运行服务器时,我遇到了以下警告:

WARNINGS:
exam.Author.author: (fields.W342) Setting unique=True on a ForeignKey has the same effect as using a OneToOneField.
HINT: ForeignKey(unique=True) is usually better served by a OneToOneField.

我该怎么办?

【问题讨论】:

我不明白你的问题。警告正在为您提供信息。 警告!= 错误。 OneToOne 字段已经保证了唯一性。 我没有唯一选项或 OneToOneField!警告表示什么? 看看OneToOneField的来源:github.com/django/django/blob/master/django/db/models/fields/… 【参考方案1】:

简而言之,Django 要求您将 ForeignKey 字段替换为:

author = models.OneToOneField(UserProfile, blank=False, primary_key=True)

另外,我建议添加一个 on_delete 键,并使其类似于:

author = models.OneToOneField(UserProfile, blank=False, primary_key=True, on_delete=models.CASCADE)

参考: https://docs.djangoproject.com/en/3.2/topics/db/examples/one_to_one/

【讨论】:

【参考方案2】:

作为Daniel said,您最好使用OneToOneField

可以在this Stack Overflow Question 找到关于为什么会这样的一个很好的解释。

【讨论】:

【参考方案3】:

primary_key 暗示 unique=True。因此,正如警告所说,您可能应该使用 OneToOneField。

【讨论】:

以上是关于在 ForeignKey 上设置 unique=True 与使用 OneToOneField 的效果相同的主要内容,如果未能解决你的问题,请参考以下文章

Django:unique_together 是不是以与 ForeignKey 相同的方式暗示 db_index=True?

FOREIGN KEY 外键约束; UNIQUE和PRIMARY KEY 主键约束CREATE INDEX建立索引的使用

MySQL:INDEX、UNIQUE、FOREIGN KEY 和 PRIMARY KEY 有啥区别?

如何在 MySQL 中有一个涉及 ForeignKey 字段的 unique_together 约束?

Django unique_together 与可为空的 ForeignKey

Django:扩展用户时,最好使用 OneToOneField(User) 或 ForeignKey(User, unique=True)?