Python FastAPI中如何用typing和Pydantic定义Optional子可选模型并解决报错
解决方案
你遇到的
TypeError: typing.Union[pydantic.main.stats, NoneType] is not a generic class报错,本质是可选子模型的类型声明语法不符合Pydantic规范导致的。
正确创建可选子模型的方法
1、静态定义方式(最常用)
先定义子模型,再在父模型中将子模型类型包裹在Optional中,默认值设为None即可:
from typing import Optional, List from pydantic import BaseModel # 定义子模型 class Stats(BaseModel): # 此处填写子模型的自有字段,示例如下 pv: int uv: Optional[int] = None # 父模型中声明可选子模型 class ParentModel(BaseModel): name: str # 可选子模型核心写法:Optional[子模型类] = None stats: Optional[Stats] = None
2、动态创建方式(使用create_model)
如果需要动态生成模型,可选子模型的字段声明格式为(Optional[子模型类], None):
from typing import Optional, List from pydantic import BaseModel, create_model # 动态创建子模型 Stats = create_model( "Stats", pv=(int, ...), uv=(Optional[int], None) ) # 动态创建带可选子模型的父模型 ParentModel = create_model( "ParentModel", name=(str, ...), # 可选子模型的字段定义格式:(类型, 默认值) stats=(Optional[Stats], None) )
常见错误排查
- 不要颠倒
Optional和子模型的顺序,禁止写Stats[Optional],必须是Optional[Stats] - 如果你使用Pydantic V2版本,也可以用更简洁的联合类型写法:
stats: Stats | None = None - 确认所有自定义模型都继承了
BaseModel,不要漏写继承关系 - 如果使用
Union声明可选类型,正确写法为Union[Stats, None],不要在Union外层或子模型后加多余的方括号
内容的提问来源于stack exchange,提问作者Abhishek Ratnam
相关产品推荐
相关产品推荐

