You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Pydantic 1.10.9中直接捕获自定义字段缺失异常?

在Pydantic 1.10.9中直接捕获验证器自定义异常的方案

在Pydantic 1.10.9版本中,默认情况下验证器抛出的异常会被统一包裹到ValidationError中,无法直接通过except MissingPhoneNumber捕获。但可以通过以下两种方式实现你想要的效果:

方案一:解析ValidationError并重新抛出自定义异常

捕获ValidationError后,遍历错误列表,识别对应的自定义异常类型并重新抛出,这样就能在后续的except块中直接捕获目标异常:

from pydantic import BaseModel, validator, ValidationError
from typing import Optional

class MissingPhoneNumber(ValueError):
    pass

class SMS(BaseModel):
    id: str       
    phone_number: Optional[str] = None
    
    @validator('phone_number', always=True)
    def phone_number(cls, v):
        if not v:
            raise MissingPhoneNumber("手机号不能为空")
        return v

if __name__ == '__main__':
    try:
        event = SMS(id="123")
    except ValidationError as e:
        # 遍历错误项,匹配自定义异常类型
        for error in e.errors():
            if error['type'] == 'value_error.missingphonenumber':
                raise MissingPhoneNumber() from e
        # 如果不是目标异常,重新抛出原ValidationError
        raise
    except MissingPhoneNumber:
        print('caught Exception')

方案二:自定义模型创建方法,手动执行验证

绕开Pydantic的验证器包装逻辑,在自定义的创建方法中完成验证并直接抛出自定义异常:

from pydantic import BaseModel
from typing import Optional

class MissingPhoneNumber(ValueError):
    pass

class SMS(BaseModel):
    id: str       
    phone_number: Optional[str] = None
    
    @classmethod
    def create(cls, **kwargs):
        # 先实例化模型(基础类型验证)
        instance = cls(**kwargs)
        # 手动执行自定义验证逻辑
        if not instance.phone_number:
            raise MissingPhoneNumber("手机号不能为空")
        return instance

if __name__ == '__main__':
    try:
        event = SMS.create(id="123")
    except MissingPhoneNumber:
        print('caught Exception')

说明:方案一保留了Pydantic的完整验证能力,仅针对目标异常做重新抛出;方案二更贴近你想要的直接捕获逻辑,但需要手动处理自定义验证逻辑。

内容的提问来源于stack exchange,提问作者Jeroen Vermunt

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.21 03:10:27