Django 中的模型
模型是所有 ORM 的核心。 模型是应用程序将要处理的数据的表现形式。 可以是人员、产品、类别或应用程序所需的任何其他形式的数据。
创建模型
在 Django 中,模型是从 django.models.Model
继承功能集合的任何类。 该集合包含多种方法,你可以使用这些方法来查询数据库,创建新条目以及保存更新。 还可以定义字段,设置元数据以及在模型之间建立关系。
如果想创建 Product
和 Category
两个模型,则需要添加两个类:
from django.db import models
class Product(models.Model):
# details would go here
pass
class Category(models.Model):
# details would go here
pass
添加方法
在我们讨论如何为模型配置数据之前,需要强调的是模型属于 Python 类。 因此,你既可以添加方法,也可以覆盖 Django.models.Model
提供的或所有 Python 对象固有的方法。
尤其要强调的一种方法是 __str__
。 未指定任何字段的情况下,可以使用此方法显示对象。 如果 Product
有 name
字段(稍后我们将看到),你可以通过重写 __str__
将其作为 Product
默认字符串表示形式返回。
class Product(models.Model):
name = models.TextField()
def __str__(self):
return self.name
添加字段
字段定义模型的数据结构。 字段可能包括项目名称、创建日期、价格或模型需要存储的任何其他数据片段。
不同的数据片段具有不同的数据类型、验证规则和其他形式的元数据。 Django ORM 包含一组丰富的选项,你可以根据规范使用这些选项来配置模型的字段。 ORM 是可扩展的,因此可以根据需要创建自己的规则。
定义字段类型
所有字段的元数据的核心部分都是它将存储的数据类型,如字符串或数字。 字段类型映射到数据库类型和 HTML 表单控件类型(如文本框或复选框)。 Django 包括多个字段类型,如:
CharField
:单行文本。TextField
:多行文本。BooleanField
:布尔 true/false 选项。DateField
:日期。TimeField
:时间。DateTimeField
:日期和时间。URLField
:URL。IntegerField
:整数。DecimalField
:固定精度的十进制数。
要将字段添加到 Product
和 Category
类,可能会使用以下代码:
from django.db import models
class Product(models.Model):
name = models.TextField()
price = models.DecimalField()
creation_date = models.DateField()
class Category(models.Model):
name = models.TextField()
字段选项
你可以使用字段选项添加允许 NULL 或空白值的元数据,或将字段标记为唯一。 还可以设置验证选项并为验证错误提供自定义消息。
与字段类型一样,字段选项会映射到数据库中的相应设置。 规则将在 Django 为你生成的任何表单中强制执行。
字段选项会传递到字段本身的函数中。 不同字段可能支持不同的选项。 常见的选项有:
null
- 允许 NULL 值的布尔选项。
- 默认值为
False
。
blank
- 允许空白值的布尔选项。
- 默认值为
False
。
default
- 如果未提供字段的值,则允许配置默认值。
- 如果要将默认值设置为数据库
null
,请将default
设置为None
。
unique
- 此字段必须包含一个唯一值。
- 默认值为
False
。
min_length
和max_length
- 与字符串类型一起用于识别最小和最大的字符串长度。
- 默认值为
None
。
min_value
和max_value
- 与数字类型一起用于识别最小和最大的值。
auto_now
和auto_now_add
。- 与日期/时间类型一起用于指示是否应该使用当前时间。
auto_now
始终在保存时将字段设置为当前时间,这对last_update
字段很有帮助。auto_now_add
始终在创建时将字段设置为当前时间,这对creation_date
字段很有帮助。
备注
值 null
和 blank
看起来相似,但在数据库术语中有不同含义。 null
是指缺少值,而 blank
专指空值。
要将选项添加到模型,代码如下所示:
from django.db import models
class Product(models.Model):
name = models.TextField(max_length=50, min_length=3, unique=True)
price = models.DecimalField(min_value=0.99, max_value=1000)
creation_date = models.DateField(auto_now_add=True)
class Category(models.Model):
name = models.TextField(max_length=50, min_length=3, unique=True)
键和关系
在关系数据库中,标准做法是表中的每一行都有一个主键,通常是自动递增的整数。 Django 的 ORM 会自动将此键添加到你创建的每个模型,方法是添加一个名为 id
的字段。
如果要重写此行为,可以将你想使用的字段设置为主键。 但在大多数情况下,你应该依赖 Django 的 id
字段。
关系数据库还包含表之间的关系。 产品对应类别,员工对应经理,而汽车对应制造商。 Django 的 ORM 支持所有你想要在模型之间创建的关系。
最常见的关系是“一对多”,在技术层面上称为外键关系。 在外键关系中,多个项目共享一个特性。 例如,将多个产品分组到一个类别。 要为此关系建模,请使用 ForeignKey
字段。
要创建关系,请将 ForeignKey
字段添加到子对象。 如果产品被分组到多个类别,则为 Product
类添加 category
属性,并将类型设置为 ForeignKey
。
Django 自动为父级添加属性,以提供对名为 <child>_set
的所有子级的访问权限,其中 <child>
是子对象的名称。 在我们的示例中,Category
将自动添加 product_set
,以提供对类别中所有产品的访问权限。
ForeignKey
有一个必需参数 on_delete
。 此参数向 Django 表明在删除父级时要执行的操作。 也就是说,如果我们删除类别,会对该类别的产品造成什么影响?
两种最常见的选项是:
CASCADE
,如果在示例中删除了某个类别,则将删除所有产品。PROTECT
,如果尝试删除包含产品的某个类别,则将返回错误。
备注
在大多数情况,你会使用 PROTECT
。
可以使用以下代码来更新模型以创建关系:
from django.db import models
class Product(models.Model):
name = models.TextField()
price = models.DecimalField()
creation_date = models.DateField()
category = models.ForeignKey(
'Category', #The name of the model
on_delete=models.PROTECT
)
class Category(models.Model):
name = models.TextField()
# product_set will be automatically created