目录
1. HTTP请求方法和幂等性
- 幂等性的定义
- 常见的HTTP请求方法
- GET
- DELETE
- POST
- PUT
- HTTP请求方法的特性
- GET请求
- POST请求
- POST和PUT的区别
2. Pydantic
- 什么是Pydantic?
- 主要特点
- 数据验证
- 类型转换
- 基于类的定义
- 嵌套模型支持
- 集成性强
- 配置灵活
- 简单示例
- 高级功能
- 字段约束
- 自定义验证逻辑
- 应用场景
3. 在FastAPI中使用Path函数
- 路径参数校验的基本用法
- 数值校验
- 常见校验条件
- 示例:整数校验
详细内容
1. HTTP请求方法和幂等性
幂等性的定义
幂等性(idempotence)是指使用相同的请求多次产生相同的结果。例如,GET和DELETE请求就是幂等的,而POST和PUT请求则不是。
常见的HTTP请求方法
- GET:用于请求指定资源,是幂等的。
- DELETE:用于删除指定资源,是幂等的。
- POST:用于向指定资源提交数据,数据被包含在请求体中,不是幂等的。
- PUT:用于向指定资源位置上传新内容,如果该资源已存在则会被覆盖,是幂等的。
HTTP请求方法的特性
- GET请求:可被缓存,保留在浏览器历史记录中,可被收藏为书签,但不适合处理敏感数据,有长度限制,只应用于取回数据。
- POST请求:不会被缓存,不保留在浏览器历史记录中,不能被收藏为书签,但对数据长度没有要求。
POST和PUT的区别
- POST:通常用于提交新资源,资源标识由服务端生成。
- PUT:通常用于更新现有资源,资源标识由客户端提供。
2. Pydantic
什么是Pydantic?
Pydantic 是一个用于数据验证和设置管理的 Python 库。它基于类注解(type annotations)来定义数据模型,并提供自动化的数据验证、转换和错误处理功能。
主要特点
- 数据验证:Pydantic 能够自动验证传入数据是否符合模型中定义的类型和约束。如果数据不符合要求,会抛出详细的错误信息。
- 类型转换:Pydantic 会尝试将输入数据转换为指定的类型。例如,字符串 "1" 可以被转换为整数 1。
- 基于类的定义:数据模型通过继承 pydantic.BaseModel 类来定义。模型中的字段可以使用 Python 的类型注解进行声明。
- 嵌套模型支持:Pydantic 支持复杂的嵌套数据结构,可以轻松处理嵌套对象。
- 集成性强:Pydantic 广泛用于 FastAPI 等现代 Web 框架中,作为数据模型的核心工具。
- 配置灵活:提供了丰富的配置选项,例如自定义错误消息、禁用额外字段等。
简单示例
from pydantic import BaseModel, ValidationError
# 定义一个数据模型
class User(BaseModel):
id: int
name: str
is_active: bool = True # 默认值
# 正确的数据
user_data = {"id": 1, "name": "Alice", "is_active": False}
user = User(**user_data)
print(user) # 输出: id=1 name='Alice' is_active=False
# 错误的数据
try:
invalid_data = {"id": "not_an_int", "name": "Bob"}
User(**invalid_data)
except ValidationError as e:
print(e) # 输出详细的验证错误信息
高级功能
- 字段约束:可以对字段添加更多的约束,例如最小值、最大值、正则表达式匹配等。
from pydantic import Field
class Product(BaseModel):
price: float = Field(gt=0, description="Price must be greater than 0")
name: str = Field(min_length=3, max_length=50)
- 自定义验证逻辑:使用
@validator
装饰器实现自定义的验证逻辑。
from pydantic import BaseModel, validator, ValidationError
class User(BaseModel):
username: str
password: str
@validator("username")
def check_username(cls, value):
if not value:
raise ValueError("Username cannot be empty")
if len(value) < 3: # 假设用户名至少需要3个字符
raise ValueError("Username must be at least 3 characters long")
return value
@validator("password")
def check_password(cls, value):
if not value:
raise ValueError("Password cannot be empty")
if len(value) < 8:
raise ValueError("Password must be at least 8 characters long")
return value
# 示例:验证数据
try:
user = User(username="abc", password="12345678")
print("用户信息验证成功:", user)
except ValidationError as e:
print("用户信息验证失败:", e)
应用场景
- 在 FastAPI 中,Pydantic 用于定义请求体、响应体以及路径参数的模型。
- 用于解析配置文件(如 JSON、YAML),并验证其内容是否符合预期。
- 自动将用户输入的数据转换为正确的类型,并验证其合法性。
- Pydantic 可以与 SQLAlchemy 等 ORM 工具结合使用,用于数据库模型的定义和验证。
3. 在FastAPI中使用Path函数
路径参数校验的基本用法
在 FastAPI 中,路径参数可以通过 Path
函数进行声明和校验。Path
可以附加元数据(如标题、描述等),并支持数值范围的校验。
from typing import Annotated
from fastapi import FastAPI, Path, HTTPException
app = FastAPI()
@app.get("/items/{item_id}")
async def read_items(
item_id: Annotated[int, Path(title="The ID of the item to get", ge=1)]
):
if item_id <= 0:
raise HTTPException(status_code=400, detail="Item ID must be a positive integer")
results = {"item_id": item_id}
return results
4.数值校验
FastAPI 支持对路径参数进行数值范围的校验。常见的校验条件包括:
ge
(greater than or equal):大于等于某个值。gt
(greater than):严格大于某个值。le
(less than or equal):小于等于某个值。lt
(less than):严格小于某个值。
示例:整数校验
@app.get("/items/{item_id}")
async def read_items(
item_id: Annotated[int, Path(title="The ID of the item to get", ge=5)]
):
results = {"item_id": item_id}
return results
@app.get("/items/{item_id}")
async def read_items(
item_id: Annotated[float, Path(title="The ID of the item to get", ge=5.5)]
):
results = {"item_id": item_id}
return results
- 访问
http://127.0.0.1:8009/items/5.6
,返回{"item_id":5.6}
。 - 访问
http://127.0.0.1:8009/items/5.4
,返回校验错误:
{
"detail": [
{
"type": "greater_than_equal",
"loc": ["path", "item_id"],
"msg": "Input should be greater than or equal to 5.5",
"input": "5.4",
"ctx": {"ge": 5.5},
"url": "https://errors.pydantic.dev/2.5/v/greater_than_equal"
}
]
}
关键点总结
导入 Path 和使用 Annotated
- 从
fastapi
模块导入Path
。 - 使用
Annotated
语法为路径参数添加类型和元数据声明。
from typing import Annotated
from fastapi import Path
元数据声明
Path
函数允许为路径参数附加元数据,例如title
、description
等。- 这些元数据会在自动生成的 API 文档中显示。
数值范围校验
- 通过
ge
、gt
、le
、lt
等参数,可以限制路径参数的数值范围。 - 如果输入不符合要求,FastAPI 会自动返回 HTTP 状态码 422 Unprocessable Entity,并附带详细的错误信息。
浮点数支持
- 路径参数不仅支持整数类型,也支持浮点数类型。
- 对于浮点数,同样可以应用相同的数值范围校验逻辑。
实际应用场景
- API 开发:确保路径参数符合预期的数据类型和范围,避免因参数错误导致程序崩溃。
- 文档生成:通过
Path
声明的元数据,FastAPI 可以自动生成详细的 API 文档(如 Swagger UI)。 - 数据安全性:通过严格的参数校验,减少因无效输入引发的安全隐患。
注意事项
- 路径参数的必填性:路径参数默认是必填的,不能设置为可选。
- 校验失败的处理:当路径参数不符合校验规则时,FastAPI 会直接返回错误响应,无需开发者额外处理。
- 性能影响:路径参数的校验通常不会显著影响性能,但在高并发场景下仍需注意。
总结
讲解了如何在 FastAPI 中使用 Path
函数对路径参数进行校验和元数据声明。通过结合 Annotated
语法,可以轻松实现类型检查、数值范围限制以及元数据附加功能。这些功能不仅提高了 API 的健壮性和安全性,还能够自动生成详细的文档,方便开发和维护。
查询参数校验和元数据声明
基础查询参数
- 在 FastAPI 中,查询参数可以通过函数参数直接定义。
from fastapi import FastAPI
app = FastAPI()
@app.get("/items/")
async def read_items(q: str | None = None):
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
if q:
results.update({"q": q})
return results
- 访问
http://127.0.0.1:8009/items/?q=test
,返回结果为:
{
"items": [
{"item_id": "Foo"},
{"item_id": "Bar"}
],
"q": "test"
}
- 未提供
q
参数(如访问http://127.0.0.1:8009/items/
),返回结果为:
{
"items": [
{"item_id": "Foo"},
{"item_id": "Bar"}
]
}
额外的校验
- 使用
Query
函数可以为查询参数添加额外的校验规则。
from fastapi import FastAPI, Query
app = FastAPI()
@app.get("/items/")
async def read_items(q: str | None = Query(default=None, max_length=5)):
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
if q:
results.update({"q": q})
return results
- 访问
http://127.0.0.1:8009/items/?q=testdata
(长度超过 5),返回错误:
{
"detail": [
{
"type": "string_too_long",
"loc": ["query", "q"],
"msg": "String should have at most 5 characters",
"input": "testdata",
"ctx": {"max_length": 5}
}
]
}
添加更多校验
- 可以为查询参数同时设置最小长度和最大长度。
from fastapi import FastAPI, Query, HTTPException
app = FastAPI()
@app.get("/items/")
async def read_items(q: str | None = Query(default=None, min_length=3, max_length=5)):
try:
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
if q:
results.update({"q": q})
return results
except Exception as e:
raise HTTPException(status_code=500, detail=f"服务器发生错误: {str(e)}")
- 如果
q
的长度不在范围内,返回相应的错误信息。
添加正则表达式
- 使用
pattern
参数可以指定查询参数必须匹配的正则表达式。
from fastapi import FastAPI, HTTPException, Query
from typing import Optional
app = FastAPI()
@app.get("/items/")
async def read_items(q: Optional[str] = Query(None, min_length=3, max_length=5, pattern=r"^test.?$")):
try:
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
if q:
results.update({"q": q})
return results
except Exception as e:
raise HTTPException(status_code=400, detail=f"查询参数错误: {str(e)}")
- 允许的值:
test
、tests
、testa
、testb
等。 - 不允许的值:
text
、testab
等。
声明为必需参数
- 如果查询参数是必需的,可以省略默认值或使用
...
显式声明。
from fastapi import FastAPI, Query, HTTPException
app = FastAPI()
@app.get("/items/")
async def read_items(q: str = Query(None, min_length=3, max_length=5, pattern=r"^test.?$")):
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
try:
if q:
results.update({"q": q})
except ValueError as e:
raise HTTPException(status_code=400, detail="Invalid query parameter") from e
return results
- 如果未提供
q
参数,返回错误:
{
"detail": [
{
"type": "missing",
"loc": ["query", "q"],
"msg": "Field required",
"input": null
}
]
}
- 使用
...
显式声明:
@app.get("/items/")
async def read_items(q: str = Query(default=..., min_length=3)):
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
return results
声明更多元数据
可以为查询参数添加更多的元数据,例如 title
和 description
,以便生成更详细的 API 文档。以下是一个示例:
from fastapi import FastAPI, Query
app = FastAPI()
@app.get("/items/")
async def read_items(
q: str | None = Query(
default=None,
title="Query string",
description="Query string for the items to search in the database",
min_length=3
)
):
results = {"items": [{"item_id": "Foo"}, {"item_id": "Bar"}]}
if q:
results.update({"q": q})
return results
关键点总结
查询参数的基础用法
查询参数可以通过函数参数直接定义,默认为可选。如果需要限制参数类型或范围,可以使用 Query
函数。
校验规则
支持以下校验规则:
min_length
:最小长度。max_length
:最大长度。pattern
:正则表达式匹配。- 必需参数:省略默认值或使用
...
。
元数据声明
可以为查询参数添加元数据(如 title
和 description
),用于生成更详细的 API 文档。
错误处理
当查询参数不符合校验规则时,FastAPI 会自动返回 HTTP 状态码 422 Unprocessable Entity,并附带详细的错误信息。
实际应用场景
- API 开发:确保查询参数符合预期的数据类型和格式,避免因参数错误导致程序崩溃。
- 文档生成:通过
Query
声明的元数据,FastAPI 可以自动生成详细的 API 文档(如 Swagger UI)。 - 数据安全性:通过严格的参数校验,减少因无效输入引发的安全隐患。
注意事项
- 默认值与必需参数:如果未声明默认值或使用
...
,则该参数为必需。如果提供了默认值,则该参数为可选。 - 校验失败的处理:当查询参数不符合校验规则时,FastAPI 会直接返回错误响应,无需开发者额外处理。
- 性能影响:查询参数的校验通常不会显著影响性能,但在高并发场景下仍需注意。
总结
讲解了如何在 FastAPI 中使用 Query
函数对查询参数进行校验和元数据声明。通过结合 Query
函数,可以轻松实现类型检查、长度限制、正则表达式匹配以及元数据附加功能。这些功能不仅提高了 API 的健壮性和安全性,还能够自动生成详细的文档,方便开发和维护。
目录结构
FastAPI 教程
- 基础概念
- FastAPI 简介
- 安装与配置
- 路由与请求处理
- 数据模型与验证
- 依赖注入
- 错误处理
- 中间件
- 安全性与认证
- 测试与调试
- 部署与生产环境
学习总结
- FastAPI 核心知识点
- 异步编程
- Pydantic 数据模型
- OpenAPI 与 Swagger UI
- 数据库集成
- 文件上传与下载
- WebSocket 支持
- 性能优化
- 常见问题与解决方案
资源链接
详细内容
FastAPI 教程
FastAPI 是一个现代、快速(高性能)的 Web 框架,用于构建 API。它基于 Python 3.7+ 的类型提示,支持异步编程,并且自动生成 OpenAPI 文档。
学习总结
FastAPI 的核心知识点包括异步编程、Pydantic 数据模型、OpenAPI 与 Swagger UI、数据库集成、文件上传与下载、WebSocket 支持、性能优化以及常见问题与解决方案。