FastAPI框架自带了对请求参数的验证,包括在路径中的参数、请求的参数以及Body中的参数,使用Path提取和验证路径参数;使用Query提取和验证?请求中的参数,使用Body将参数让客户端由body(默认application/json方式)传入。示例如下:
#示例python代码
from fastapi import FastAPI, Path, Query, Body
app = FastAPI()
# 通过get方式在URL路径中接收请求参数
@app.get("/items/{item_id}")
async def read_root1(item_id: int = Path(..., gt=0)):
return {"item_id": item_id}
# 虽然是通过post方式提交请求,但item_id仍然是在URL中通过?item_id进行请求
@app.post("/items")
async def read_root2(item_id: int = Query(..., ge=1)):
return {"item_id": item_id}
# post方式提交请求,但item_id仍然是在URL中通过?item_id进行请求
@app.post("/items")
async def read_root2(
item_id: int = Body(..., ge=1, embed=True),
item_name: str = Body(None, max_length=25)):
return {"item_id": item_id, "item_name": item_name}
第三种情况要注意,有时你明明使用的app.post方式,但是服务端接受不到数据,就是因为参数没有带上Body()方法,直接使用int=1这种默认值,这种处理虽然设置了app.post,请求的时候仍然是在URL中通过?item_id进行请求。此时使用Body再加上embed=True表示将参数名放入body实体中做为健值对来请求。另外可以不使用Body,而使用BaseModel,如下:
from typing import Optional
from fastapi import FastAPI
from pydantic import BaseModel
#定义一个model,继承BaseModel
class Item(BaseModel):
name: str
description: Optional[str] = None
price: float
tax: Optional[float] = None
app = FastAPI()
#请求是只需要写Item即可。
@app.post("/items/")
async def create_item(item: Item):
return item
继承自BaseModel的接收体只能通过POST来发送。如上面的例子中,参数有使用max_length这种设置,这是 Path, Query, Body的参数验证。这三种实现方式和使用参数方式都差不多,大同小异。列一下验证规则:
def Query(
default: Any,
*,
alias: str = None, #请求参数别名,使用了alias就必须使用alias的参数名传参。
title: str = None, #没有发现哪里有用
description: str = None, #没有发现哪里有用
gt: float = None, #大于某值
ge: float = None, #大于等于某值
lt: float = None, #小于某值
le: float = None, #小于等于某值
min_length: int = None, #最小长度
max_length: int = None, #最大长度
regex: str = None, #正则规则
deprecated: bool = None, # True表示将要是废弃的接口
**extra: Any,
)
Body的话还有一个media_type属性,默认str值为application/json,其它的就都一样的。参数没有通过验证框架就会抛出412状态码并带有detail描述的json字符串。