gpt4 book ai didi

python - 电话号码 : value_error. 的 pydantic 自定义数据类型丢失

转载 作者:行者123 更新时间:2023-12-05 01:26:09 24 4
gpt4 key购买 nike

用户的 mysql 模式

user_id     binary(16) 
first_name varchar(32)
last_name varchar(32)
email varchar(255)
phone varchar(32)
role enum('member','admin','operator')
created_on datetime
updated_on datetime
id varchar(32)

我的模型是

class UserPatchEntity(BaseModel):
user_id: Optional[UUID]
first_name: Optional[str] = Field(min_length=1, max_length=32)
last_name: Optional[str] = Field(min_length=1, max_length=32)
email: Optional[EmailStr]
phone: Optional[Phone]---------------> HERE
role: Optional[RoleType]

我想为电话号码创建一个自定义数据类型......所以我可以在多个地方使用它......我正在尝试如下

class Phone(BaseModel):
phone: str
@validator('phone')
def phone_validation(cls, v):
phone = v.phone.get("phone")
logger.debug(f"phone in 2 validator:{v}")
regex = r"^(\+)[1-9][0-9\-\(\)\.]{9,15}$"
if v and not re.search(regex, v, re.I):
raise ValueError("Phone Number Invalid.")
return v
class Config:
orm_mode = True
use_enum_values = True

通过 postman ,我正在发送

{
"phone": "+917777777777"
}

我在 postman 中看到 400 错误

[
{
"loc": [
"phone",
"phone"
],
"msg": "field required",
"type": "value_error.missing"
}
]

关于我在上面做错了什么的任何输入

最佳答案

这不起作用,因为您正在传入:

{
"phone": "+917777777777"
}

虽然模型具有结构UserPatchEntity.Phone.phone

为了完成这项工作,我看到了两个选项:

1。调整 JSON 正文(并修复 validator)

修复验证器:

class Phone(BaseModel):
phone: str
@validator("phone")
def phone_validation(cls, v):
# phone = v.phone.get("phone") # <-- This line needs to be removed.
logger.debug(f"phone in 2 validator:{v}")
regex = r"^(\+)[1-9][0-9\-\(\)\.]{9,15}$"
if v and not re.search(regex, v, re.I):
raise ValueError("Phone Number Invalid.")
return v

class Config:
orm_mode = True
use_enum_values = True

改为发送:

{
"phone": {
"phone": "+917777777777"
}
}

它现在应该可以工作了。

2。将验证器移动到父模型

我假设以下内容更符合您的要求:

class UserPatchEntity(BaseModel):
user_id: Optional[UUID]
first_name: Optional[str] = Field(min_length=1, max_length=32)
last_name: Optional[str] = Field(min_length=1, max_length=32)
email: Optional[EmailStr]
phone: Optional[str] # <-- This is a str now, everything else stays the same
role: Optional[RoleType]

@validator("phone")
def phone_validation(cls, v):
logger.debug(f"phone in 2 validator:{v}")
regex = r"^(\+)[1-9][0-9\-\(\)\.]{9,15}$"
if v and not re.search(regex, v, re.I):
raise ValueError("Phone Number Invalid.")
return v

class Config:
orm_mode = True
use_enum_values = True

有了它,您就可以像预期的那样在正文中传递 phone:

{
"phone": "+917777777777"
}

假设您使用的是 FastAPI,在这两种情况下,如果电话号码太短、太长或包含无效字符,您将收到以下错误:

{
"detail": [
{
"loc": [
"body",
"phone"
],
"msg": "Phone Number Invalid.",
"type": "value_error"
}
]
}

注意事项/提示:

  • Pydantic 有一个 constr (Constrained String) 类型,它允许您定义最小和最大长度,以及一些其他的东西。对于 phone 字段,您可以使用以下代替 str,例如:

    class UserPatchEntity(BaseModel):
    ...
    phone: Optional[
    constr(
    strip_whitespace=True,
    min_length=9,
    max_length=15,
    )
    ]

    它还允许您直接指定一个 regex 字符串,例如:

    class UserPatchEntity(BaseModel):
    ...
    phone: Optional[
    constr(
    strip_whitespace=True,
    regex=r"^(\+)[1-9][0-9\-\(\)\.]{9,15}$",
    )
    ]

    这将节省您编写显式 validator 的时间。

  • 如果您继续“直接”使用正则表达式,我会建议 compile()他们使他们更快一点。

  • 假设您使用的是 FastAPI,您可以导航到 http://localhost:8000/docs,当应用程序运行时,您会在其中找到完整的 OpenAPI 接口(interface)。您可以直接从那里发送有效负载,它还会向您显示每个端点的签名。在第一种情况下,如果您像这样定义端点:

    @router.post("/user/")
    async def post_user(user_patch_entity: UserPatchEntity):
    return user_patch_entity.phone

    它会像这样显示文档: enter image description here

关于python - 电话号码 : value_error. 的 pydantic 自定义数据类型丢失,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/70414211/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com