FastAPI与 Pydantic无法解析List[int] 类型的查询参数(多值不起作用)
我想用FastAPI和 Pydantic将多个查询参数作为列表接收,但效果并未达到预期。
示例请求:
GET /api/v1/items/guest?industries=4&industries=5&industries=6
我的Pydantic模型:
from pydantic import BaseModel
from typing import Optional, List
class GuestGetItemsSchema(BaseModel):
s: Optional[str] = None
latitude: Optional[float] = None
longitude: Optional[float] = None
industries: Optional[List[int]] = None
page_size: Optional[int] = None
next_token: Optional[str] = None
previous_token: Optional[str] = None
端点:
from fastapi import Depends
@app.get("/api/v1/items/guest")
async def get_services(schema: GuestGetItemsSchema = Depends()):
return schema
问题:
- 该
industries列表总是为空,或为None - 它无法将多个查询参数解析为一个列表
- 其他字段工作正常
我期望的结果:
{
"industries": [4, 5, 6]
}
得到的结果:
{
"industries": null
}
在使用FastAPI时,如何在Pydantic模型中正确将多个查询参数解析为一个 List[int],前提是使用 Depends()?
有没有正确的方法让FastAPI将像 ?industries=1&industries=2 这样的查询参数绑定到模型中的一个列表字段?
直接传入查询参数时可以工作,但在Pydantic模型校验时就不行。
解决方案
为了让FastAPI正确处理查询参数,您需要明确模型表示请求的哪一部分,例如:
@app.get("/api/v1/items/guest")
async def get_services(schema: Annotated[GuestGetItemsSchema, Query()]):
return schema
或者专门针对该字段:
class GuestGetItemsSchema(BaseModel):
s: Optional[str] = None
latitude: Optional[float] = None
longitude: Optional[float] = None
industries: Optional[List[int]] = Field(Query(None))
page_size: Optional[int] = None
next_token: Optional[str] = None
previous_token: Optional[str] = None
然后:
$ curl 'http://localhost:8000/api/v1/items/guest?industries=1&industries=2&industries=3'
{"s":null,"latitude":null,"longitude":null,"industries":[1,2,3],"page_size":null,"next_token":null,"previous_token":null}
否则,如自动生成的OpenAPI规范所示(尽管GET请求没有定义的请求体语义),它会假设整数列表将作为请求的 body(请求体):
{
"openapi": "3.1.0",
"info": {
"title": "FastAPI",
"version": "0.1.0"
},
"paths": {
"/api/v1/items/guest": {
"get": {
"summary": "Get Services",
"operationId": "get_services_api_v1_items_guest_get",
"parameters": [...],
"requestBody": {
"content": {
"application/json": {
"schema": {
"anyOf": [
{
"type": "array",
"items": {
"type": "integer"
}
},
{
"type": "null"
}
],
"title": "Industries"
}
}
}
},
"responses": {...}
}
}
},
"components": {...}
}
这在 文档 中确实有提及,但你需要多找一点:
提示 要声明一个类型为
list的查询参数,如上面的示例,你需要显式使用Query,否则它会被解释为请求体。
站内所有文章版权归属LeftHeroAI导航站,无授权禁止任何主体转载、抄袭、复制内容,亦不得私自架设镜像站点。一经侵权,本站将通过法律途径追责。