如何用Pydantic验证合法JSON字典?递归定义报错求解
解决Pydantic验证合法JSON结构的递归类型问题
要验证传入数据是合法的JSON结构(仅包含JSON支持的类型:null、字符串、数字、布尔值、数组、对象),你可以通过正确定义递归类型并处理Pydantic的自引用解析来解决递归错误,具体分版本实现:
Pydantic v1 解决方案
v1中需要显式处理递归引用,通过ForwardRef或字符串注解定义类型后,调用update_forward_refs()完成类型解析:
from typing import Dict, List, Union, ForwardRef from pydantic import BaseModel # 定义JSON支持的所有类型,包含递归的数组和对象 JsonValue = Union[None, str, int, float, bool, List[ForwardRef('JsonValue')], Dict[str, ForwardRef('JsonValue')]] class MyModel(BaseModel): field: JsonValue # 解析递归引用,必须调用这一步 MyModel.update_forward_refs()
也可以用字符串形式的自引用,效果一致:
from typing import Dict, List, Union from pydantic import BaseModel JsonValue = Union[None, str, int, float, bool, List['JsonValue'], Dict[str, 'JsonValue']] class MyModel(BaseModel): field: JsonValue MyModel.update_forward_refs()
Pydantic v2 解决方案
v2原生支持自引用类型,无需额外调用方法,直接定义即可:
from typing import Dict, List, Union from pydantic import BaseModel JsonValue = Union[None, str, int, float, bool, List['JsonValue'], Dict[str, 'JsonValue']] class MyModel(BaseModel): field: JsonValue
验证效果测试
- 合法JSON结构会正常通过验证:
valid_data = {"field": {"name": "Alice", "age": 30, "hobbies": ["reading", None], "active": True, "score": 95.5}} model = MyModel(**valid_data) print(model) - 包含JSON不支持的类型(如
datetime、自定义类)会触发验证错误:from datetime import datetime invalid_data = {"field": {"register_time": datetime.now()}} try: model = MyModel(**invalid_data) except Exception as e: print(e) # 输出验证错误信息
关键说明
- 必须包含
float类型:JSON的数字类型包含整数和浮点数,遗漏会导致浮点数被判定为非法 - 递归类型的核心是让Pydantic正确识别自引用关系,v1需手动触发解析,v2自动支持
内容的提问来源于stack exchange,提问作者Peter
相关产品推荐
相关产品推荐

