Fastapi报错RuntimeError: no validator found for <class ‘typing._UnionGenericAlias’>, see `arbitrary_ty
问题描述
使用FastAPI 请求体 - 嵌套模型的时候报错, 不嵌套的时候是可以的
不嵌套校验
class PredictGas(BaseModel):
predict_level: str
predict_day_is_heating_season: bool
predict_type: str = Field(default="area", description="预测类型")
heating_start_date: Union[datetime, date]
heating_end_date: Union[datetime, date]
# Optional可选类型 Optional[X]等价于Union[X, None] int=1等价于Optional[int] = 2 Union[int, float]只能传int float
model: Optional[int] = Field(default=1, title="算法模型id", description="可选不同模型调用", le=2, ge=1)
data: List[dict] = [] # List[dict] = [] 等价于 list = [] # 前者可验证list内部第一层数据结构
其中 Optional可选类型 Optional[X]等价于Union[X, None] int=1等价于Optional[int] = 2 Union[int, float]只能传int float
使用嵌套模型 (其中data是第一层列表字典数据)
其中验证流程是 从外到内层 PredictGas —>>> DataBody ----->>> (PredictParams, PastParams)
class PredictParams(BaseModel):
# is_heating = Optional[bool]
# ts: Union[datetime, date]
# low_temp = Union[int, float]
# low_temp = float
# high_temp = float
# is_heating = bool
ts = date
low_temp: float = 1.0
high_temp: float = 10.0
is_heating: bool = False
# class Config:
# arbitrary_types_allowed = True
class PastParams(BaseModel):
# ts: Union[datetime, date]
# gas_value: float
# low_temp = float
# high_temp = float
# is_heating = bool
ts: date
gas_value: float
low_temp: float = 1.0
high_temp: float = 10.0
is_heating: bool = False
class DataBody(BaseModel):
code: str
# predict_params: Union[List[PredictParams], None] =None
# predict_params: List # 不进行内层验证
predict_params: List[PredictParams]
past_params: List[PastParams]
class PredictGas(BaseModel):
predict_level: str
predict_day_is_heating_season: bool
predict_type: str = Field(default="area", description="预测类型")
heating_start_date: Union[datetime, date]
heating_end_date: Union[datetime, date]
# Optional可选类型 Optional[X]等价于Union[X, None] int=1等价于Optional[int] = 2 Union[int, float]只能传int float
model: Optional[int] = Field(default=1, title="算法模型id", description="可选不同模型调用", le=2, ge=1)
# data: List[dict] = [] # List[dict] = [] 等价于 list = [] # 前者可验证list内部第一层数据结构
# 嵌套模型校验
# data: Union[List[Image], None] = None
data: List[DataBody]
我的检验数据格式
{
"predict_level": "day",
"predict_day_is_heating_season": False,
"predict_type": "area",
"heating_start_date": "2023-10-10",
"heating_end_date": "2024-3-10",
"model": 1,
"data": [
{
"code": "1",
"predict_params": [
{
"ts": "2023-10-12",
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-13",
"low_temp": -1,
"high_temp": 2,
"is_heating": True
}
],
"past_params": [
{
"ts": "2023-10-05",
"gas_value": 1555,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-06",
"gas_value": 2000,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-07",
"gas_value": 2000,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-08",
"gas_value": 1555,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-09",
"gas_value": 1555,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-10",
"gas_value": 1555,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
},
{
"ts": "2023-10-11",
"gas_value": 1555,
"low_temp": -1,
"high_temp": 2,
"is_heating": True
}
]
}
]
}
报错情况
当我最内层嵌套的class使用 Union的时候会报错RuntimeError: no validator found for <class ‘typing._UnionGenericAlias’>, see `arbitrary_ty
github提供的解决方案
用了上面的解决方式后fastapi启动不报错,但是接口测试报错
最终定位发现,使用python3.10版本 将Union[int, float]的使用方式换位low_temp = int, | float这种就好了
如果python3.10一下版本的话 使用单种类型验证才可以例如:
class PredictParams(BaseModel):
ts = date
low_temp: float = 1.0
high_temp: float = 10.0
is_heating: bool = False