postgres 上的 Django unique_together:由 ORM 或 DB 强制执行?

Posted

技术标签:

【中文标题】postgres 上的 Django unique_together:由 ORM 或 DB 强制执行?【英文标题】:Django unique_together on postgres: enforced by ORM or DB? 【发布时间】:2011-10-02 09:24:01 【问题描述】:

当我查看包含 unique_together 语句的 models.py 的 sqlall 时,我没有注意到任何看起来像是强制执行的东西。

在我看来,我可以想象这些知识可能会帮助数据库优化查询,如下所示:

“我已经找到了包含垃圾邮件 42 和鸡蛋 91 的行,因此在搜索鸡蛋 91 时,我不再需要检查包含垃圾邮件 42 的行。”

这些知识对数据库有帮助吗?

我没有以这种方式强制执行它是对的吗(即它仅由 ORM 强制执行)?

如果两者都是,这是一个缺陷吗?

【问题讨论】:

文档说它是在数据库级别强制执行的,这就足够了吗? :) 嗯,你能链接吗?我看了看,但没看到。即使是这样,我也看不出在 sqlall 输出中的哪个位置发生了强制执行。 这里是:docs.djangoproject.com/en/dev/ref/models/options/… 好的,所以文档确实这么说。但是什么声明强制执行它? 【参考方案1】:

这是一个示例。假设您有模型:

class UserConnectionRequest(models.Model):
    sender = models.ForeignKey(UserProfile, related_name='sent_requests')
    recipient = models.ForeignKey(UserProfile, related_name='received_requests')
    connection_type = models.PositiveIntegerField(verbose_name=_(u'Connection type'), \
                                                  choices=UserConnectionType.choices())

    class Meta:
        unique_together = (("sender", "recipient", "connection_type"),)

运行 sqlall 它返回:

CREATE TABLE "users_userconnectionrequest" (
    "id" serial NOT NULL PRIMARY KEY,
    "sender_id" integer NOT NULL REFERENCES "users_userprofile" ("id") DEFERRABLE INITIALLY DEFERRED,
    "recipient_id" integer NOT NULL REFERENCES "users_userprofile" ("id") DEFERRABLE INITIALLY DEFERRED,
    "connection_type" integer,
    UNIQUE ("sender_id", "recipient_id", "connection_type")
)

当此模型在 DB 上正确同步时,它具有唯一约束 (postgres):

约束 users_userconnectionrequest_sender_id_2eec26867fa22bfa_uniq 唯一的(sender_id、receiver_id、connection_type),

【讨论】:

以上是关于postgres 上的 Django unique_together:由 ORM 或 DB 强制执行?的主要内容,如果未能解决你的问题,请参考以下文章

Postgres:使用 django 对 json 键进行值查询

[PostgreSQL] Ensure Uniqueness in Postgres

如何在 django 的核心模型中添加“unique_together”约束?

在从 Postgres 9.4 到 Greenplum 的数据迁移过程中,我应该如何处理我的 UNIQUE 约束

Postgres的CREATE UNIQUE INDEX似乎停留了一段时间

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