# Django 3.2.11.dev 文档

# 约束参考

本模块中定义的类可以创建数据库约束。它们被添加到模型中 `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 3.2.

一个包含在覆盖的唯一索引中的字段名称的列表或元组，作为非键列。这允许只用索引扫描，用于只选择包含的字段（ `include` ）和只过滤唯一字段（ `fields` ）的查询。

例子：

    UniqueConstraint(name='unique_booking', fields=['room', 'date'], include=['full_name'])

将允许对 `room` 和 `date` 进行过滤，也可以选择 `full_name`，同时只从索引中获取数据。

`include` 只在 PostgreSQL 上支持。

Non-key columns have the same database restrictions as `Index.include`.

### `opclasses`

`UniqueConstraint.``opclasses`

New in Django 3.2.

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 以外的数据库来说是被忽略的。