约束参考
本模块中定义的类可以创建数据库约束。它们被添加到模型中 Meta.constraints
选项中。
引用内置约束
约束是在 django.db.models.constraint
中定义的,但为了方便,它们被导入到 django.db.models
中。标准的惯例是使用 from django.db import models
作为 models.<Foo>Constraint
。
抽象基类中的约束
你必须始终为约束指定一个唯一的名称。因此,你通常不能在抽象基类上指定一个约束,因为 Meta.craces
选项是由子类继承的,每次的属性值(包括 name
)都完全相同。为了解决名称碰撞的问题,名称的一部分可能包含 '%(app_label)s'
和 '%(class)s'
,它们分别被具体模型的小写应用标签和类名所代替。例如 CheckConstraint(check=Q(age__gte=18),name='%(app_label)s_%(class)s_is_adult')
。
约束的验证
一般来说,在 full_clean()
期间,约束条件 不会被 检查,也不会引起 ValidationError
。而是在 save()
时,你会得到一个数据库完整性错误。没有 condition
的 UniqueConstraint
(即非部分唯一约束)在这方面是不同的,它们利用了现有的 validate_unique()
逻辑,从而实现了两阶段验证。除了在 save()
上出现 IntegrityError
外,在模型验证过程中,当 UniqueConstraint
被违反时,ValidationError
也会被引发。
CheckConstraint
class CheckConstraint
(**, check, name*)
在数据库中创建一个检查约束
check
CheckConstraint.``check
一个 Q
对象或布尔值 Expression
,它指定了你要强制约束的检查。
例如,CheckConstraint(check=Q(age__gte=18), name='age_gte_18')
确保年龄字段永远不小于 18。
Changed in Django 3.1:
增加了对布尔 Expression
的支持。
name
CheckConstraint.``name
约束的名称。你必须始终为约束指定一个唯一的名称。
UniqueConstraint
class UniqueConstraint
(**, fields, name, condition=None, deferrable=None, include=None, opclasses=()*)
在数据库中创建一个唯一约束。
fields
UniqueConstraint.``fields
一个字段名的列表,它指定了你要强制约束的唯一列集。
例如,UniqueConstraint(field=['room', 'date'], name='unique_booking')
确保每个房间在每个日期只能被预订一次。
name
UniqueConstraint.``name
约束的名称。你必须始终为约束指定一个唯一的名称。
condition
UniqueConstraint.``condition
一个 Q
对象,用于指定你想要强制执行的约束条件。
例子:
UniqueConstraint(fields=['user'], condition=Q(status='DRAFT'), name='unique_draft_user')
确保每个用户只有一份草稿。
这些条件与 Index.condition
具有相同的数据库限制。
deferrable
UniqueConstraint.``deferrable
New in Django 3.1.
设置该参数,可创建一个可推迟的唯一约束。接受的值是 Deferrable.DEFERRED
或 Deferrable.IMMEDIATE
。例如:
from django.db.models import Deferrable, UniqueConstraint
UniqueConstraint(
name='unique_order',
fields=['order'],
deferrable=Deferrable.DEFERRED,
)
默认情况下,约束条件是不推迟的。推迟的约束条件在事务结束前不会被强制执行。即时约束将在每条命令后立即执行。
MySQL,MariaDB 和 SQLite。
在 MySQL、MariaDB 和 SQLite 上,可推迟的唯一约束被忽略,因为它们都不支持。
警告
推迟的唯一约束可能导致 性能惩罚 。
include
UniqueConstraint.``include
New in Django Development version.
A list or tuple of the names of the fields to be included in the covering unique index as non-key columns. This allows index-only scans to be used for queries that select only included fields (include
) and filter only by unique fields (fields
).
例子:
UniqueConstraint(name='unique_booking', fields=['room', 'date'], include=['full_name'])
will allow filtering on room
and date
, also selecting full_name
, while fetching data only from the index.
include
is supported only on PostgreSQL.
Non-key columns have the same database restrictions as Index.include
.
opclasses
UniqueConstraint.``opclasses
New in Django Development version.
The names of the PostgreSQL operator classes to use for this unique index. If you require a custom operator class, you must provide one for each field in the index.
例子:
UniqueConstraint(name='unique_username', fields=['username'], opclasses=['varchar_pattern_ops'])
creates a unique index on username
using varchar_pattern_ops
.
opclasses
对于 PostgreSQL 以外的数据库来说是被忽略的。