Pydantic¶
.
Pydantic 是 Python 中使用最广泛的数据验证库。
快速且可扩展,Pydantic 与你的代码检查器/集成开发环境/大脑配合良好。以纯的、规范的 Python 3.8+ 定义数据应该如何;使用 Pydantic 对其进行验证。
from datetime import datetime
from typing import Tuple
from pydantic import BaseModel
class Delivery(BaseModel):
timestamp: datetime
dimensions: Tuple[int, int]
m = Delivery(timestamp='2020-01-02T03:04:05Z', dimensions=['10', '20'])
print(repr(m.timestamp))
#> datetime.datetime(2020, 1, 2, 3, 4, 5, tzinfo=TzInfo(UTC))
print(m.dimensions)
#> (10, 20)
问题
“为什么 Pydantic 是这样命名的?”
“Pydantic”这个名字是“Py”和“pedantic”的混合词。“Py”部分表示该库与 Python 相关,而“pedantic”指的是该库在数据验证和类型强制方面的细致方法。
综合这些元素,“Pydantic”描述了我们的 Python 库,它提供了注重细节、严格的数据验证。
我们意识到具有讽刺意味的是,Pydantic V1 在其验证中并不严格,所以如果我们很“吹毛求疵”的话,在 V2 版本之前,“Pydantic”是一个用词不当的名称😉。
为什么使用 Pydantic?¶
-
由类型提示驱动——借助 Pydantic,模式验证和序列化由类型注释控制;学习的更少,编写的代码更少,并且与您的 IDE 和静态分析工具集成。了解更多……
-
速度——Pydantic 的核心验证逻辑是用 Rust 编写的。因此,Pydantic 是 Python 中最快的数据验证库之一。了解更多……
-
JSON 模式——Pydantic 模型可以生成 JSON 模式,从而便于与其他工具进行集成。了解更多……
-
严格模式和宽松模式——Pydantic 可以在
strict=True
模式(数据不进行转换)或strict=False
模式下运行(在适当的情况下,Pydantic 尝试将数据强制转换为正确类型)。了解更多…… -
数据类、类型字典等——Pydantic 支持对许多标准库类型的验证,包括
dataclass
和TypedDict
。了解更多…… -
自定义——Pydantic 允许自定义验证器和序列化器以多种强大方式改变数据的处理方式。了解更多……
-
生态系统——PyPI 上约有 8000 个包使用 Pydantic,包括像 FastAPI、 huggingface、Django Ninja、SQLModel 和 LangChain 这样极受欢迎的库。了解更多……
-
经过实战检验——Pydantic 每月被下载超过 7000 万次,被所有 FAANG 公司以及纳斯达克 25 家最大公司中的 20 家所使用。如果你正试图用 Pydantic 做某事,那么可能其他人已经做过了。了解更多……
安装 Pydantic 就像这样简单: pip install pydantic
Pydantic 使用例子¶
from datetime import datetime
from pydantic import BaseModel, PositiveInt
class User(BaseModel):
id: int # (1)!
name: str = 'John Doe' # (2)!
signup_ts: datetime | None # (3)!
tastes: dict[str, PositiveInt] # (4)!
external_data = {
'id': 123,
'signup_ts': '2019-06-01 12:22', # (5)!
'tastes': {
'wine': 9,
b'cheese': 7, # (6)!
'cabbage': '1', # (7)!
},
}
user = User(**external_data) # (8)!
print(user.id) # (9)!
#> 123
print(user.model_dump()) # (10)!
"""
{
'id': 123,
'name': 'John Doe',
'signup_ts': datetime.datetime(2019, 6, 1, 12, 22),
'tastes': {'wine': 9, 'cheese': 7, 'cabbage': 1},
}
"""
-
id
的类型是int
;仅注释声明告知 Pydantic 该字段是必需的。如果可能,字符串、字节或浮点数将被强制转换为整数;否则将引发异常。 -
name
是一个字符串;因为它有默认值,所以不需要。 -
signup_ts
是一个必填的datetime
字段,但值None
可以提供;Pydantic 将处理 Unix 时间戳整数(例如1496498400
)或表示日期和时间的字符串。 -
tastes
是一个键为字符串且值为正整数的字典。PositiveInt
类型是Annotated[int, annotated_types.Gt(0)]
的简写。 -
这里的输入是一个 ISO8601 格式的日期时间,Pydantic 将把它转换为一个
datetime
对象。 -
关键在这里是
bytes
,但 Pydantic 会负责将其强制转换为字符串。 -
同样地,Pydantic 会将字符串
'1'
强制转换为整数1
。 -
这里通过将外部数据作为关键字参数传递给
User
来创建User
的实例 -
我们可以将字段作为模型的属性来访问
-
我们可以将模型转换为带有
model_dump()
的字典
如果验证失败,Pydantic 会引发一个错误并详细说明哪里出错了:
# continuing the above example...
from pydantic import ValidationError
class User(BaseModel):
id: int
name: str = 'John Doe'
signup_ts: datetime | None
tastes: dict[str, PositiveInt]
external_data = {'id': 'not an int', 'tastes': {}} # (1)!
try:
User(**external_data) # (2)!
except ValidationError as e:
print(e.errors())
"""
[
{
'type': 'int_parsing',
'loc': ('id',),
'msg': 'Input should be a valid integer, unable to parse string as an integer',
'input': 'not an int',
'url': 'https://pydantic.com.cn/errors/validation_errors#int_parsing',
},
{
'type': 'missing',
'loc': ('signup_ts',),
'msg': 'Field required',
'input': {'id': 'not an int', 'tastes': {}},
'url': 'https://pydantic.com.cn/errors/validation_errors#missing',
},
]
"""
-
输入数据在这里有误——
id
不是有效的整数,且signup_ts
缺失 -
User(...)
将引发一个带有错误列表的ValidationError
谁在使用 Pydantic?¶
数百个组织和包正在使用 Pydantic。全球一些使用 Pydantic 的著名公司和组织包括:
对于使用 Pydantic 的更全面的开源项目列表,请参阅 github 上的依赖项列表,或者您可以在 awesome-pydantic 中找到一些使用 Pydantic 的很棒的项目。
本文总阅读量次