跳到内容

Body - 字段

与您可以使用 QueryPathBody路由函数参数声明额外的验证和元数据的方式相同,您也可以使用 Pydantic 的 Field 在 Pydantic 模型内部声明验证和元数据。

导入 Field

首先,您需要导入它

from typing import Annotated

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: str | None = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: float | None = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Annotated[Item, Body(embed=True)]):
    results = {"item_id": item_id, "item": item}
    return results
🤓 其他版本和变体
from typing import Annotated, Union

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: Union[float, None] = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Annotated[Item, Body(embed=True)]):
    results = {"item_id": item_id, "item": item}
    return results

提示

如果可能,请优先使用 Annotated 版本。

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: str | None = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: float | None = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item = Body(embed=True)):
    results = {"item_id": item_id, "item": item}
    return results

提示

如果可能,请优先使用 Annotated 版本。

from typing import Union

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: Union[float, None] = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item = Body(embed=True)):
    results = {"item_id": item_id, "item": item}
    return results

警告

请注意,Field 是直接从 pydantic 导入的,而不是从 fastapi 导入的,而其他所有(QueryPathBody 等)都是从 fastapi 导入的。

声明模型属性

然后,您可以在模型属性中使用 Field

from typing import Annotated

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: str | None = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: float | None = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Annotated[Item, Body(embed=True)]):
    results = {"item_id": item_id, "item": item}
    return results
🤓 其他版本和变体
from typing import Annotated, Union

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: Union[float, None] = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Annotated[Item, Body(embed=True)]):
    results = {"item_id": item_id, "item": item}
    return results

提示

如果可能,请优先使用 Annotated 版本。

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: str | None = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: float | None = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item = Body(embed=True)):
    results = {"item_id": item_id, "item": item}
    return results

提示

如果可能,请优先使用 Annotated 版本。

from typing import Union

from fastapi import Body, FastAPI
from pydantic import BaseModel, Field

app = FastAPI()


class Item(BaseModel):
    name: str
    description: Union[str, None] = Field(
        default=None, title="The description of the item", max_length=300
    )
    price: float = Field(gt=0, description="The price must be greater than zero")
    tax: Union[float, None] = None


@app.put("/items/{item_id}")
async def update_item(item_id: int, item: Item = Body(embed=True)):
    results = {"item_id": item_id, "item": item}
    return results

Field 的工作方式与 QueryPathBody 相同,它具有所有相同的参数,等等。

技术细节

实际上,QueryPath 和您接下来将看到的其他参数都是创建通用 Param 类的子类的对象,而 Param 类本身又是 Pydantic 的 FieldInfo 类的子类。

而 Pydantic 的 Field 也返回 FieldInfo 的实例。

Body 也直接返回 FieldInfo 的子类的对象。还有其他将在稍后介绍的类是 Body 类的子类。

请记住,当您从 fastapi 导入 QueryPath 以及其他参数时,它们实际上是返回特殊类的函数。

提示

请注意,每个带有类型、默认值和 Field 的模型属性的结构,都与路由函数的参数结构相同,只是将 PathQueryBody 替换为 Field

添加额外信息

您可以在 FieldQueryBody 等中声明额外信息,它将被包含在生成的 JSON Schema 中。

稍后在文档中,当您学习声明示例时,将了解更多关于添加额外信息的内容。

警告

传递给 Field 的额外键也将存在于您的应用程序生成的 OpenAPI Schema 中。由于这些键不一定是 OpenAPI 规范的一部分,因此一些 OpenAPI 工具,例如 OpenAPI 验证器,可能无法处理您生成的 Schema。

总结

您可以使用 Pydantic 的 Field 为模型属性声明额外的验证和元数据。

您还可以使用额外的关键字参数来传递其他 JSON Schema 元数据。