您的位置:

处理fastapi出现报错HTTPException(status_code=422, detail=e.errors())

  发布时间:2023-02-09 14:04:50
报错的原因在 Python 中使用 FastAPI 时表示请求参数验证失败。status_code=是 HTTP 状态码,表示请求格式正确,但是由于语义错误无法处理。detail=e.errors() 表示验证错误的详细信息。FastAPI提供了一组内置验证器,例如等,以及 Pydantic 模型来验证请求参数。例如,使用 Pydantic 模型定义请求参数并使用 @validate_query 标记要验证的参数。

报错的原因

HTTPException(status_code=422, detail=e.errors()) 在 Python 中使用 FastAPI 时表示请求参数验证失败。 status_code=422 是 HTTP 状态码,表示请求格式正确,但是由于语义错误无法处理。detail=e.errors() 表示验证错误的详细信息。

如何解决

可以通过对请求参数进行验证来解决这个问题。FastAPI提供了一组内置验证器,例如 `min_length`, `max_length`, `range` 等,以及 Pydantic 模型来验证请求参数。例如,使用 Pydantic 模型定义请求参数并使用 @validate_query 标记要验证的参数。

例如:


from fastapi import FastAPI, Query, HTTPException
from pydantic import BaseModel, validator

app = FastAPI()

class Item(BaseModel):
    name: str
    price: float

    @validator("price")
    def price_must_be_positive(cls, value):
        if value <= 0:
            raise ValueError("Price must be greater than zero.")
        return value

@app.get("/items/{item_id}")
def read_item(item_id: int, item: Item = Query(None, alias="item", title="The item to get", description="Item description")):
    if item is None:
        raise HTTPException(status_code=404, detail="Item not found")
    return item

在这个例子中,我们用Pydantic模型定义了一个Item,并使用validator装饰器来验证它的price字段,如果price<=0 那么就抛出异常。

还可以自定义验证函数,使用`@app.query_param()`或`@app.path_param()`装饰器来验证请求参数。

另外,当验证失败时,可以使用 `raise HTTPException(status_code=422, detail="Validation Error: {error_msg}")` 或者 `raise HTTPException(status_code=422, detail=e.errors())` 来返回验证错误。

使用例子

当然,下面是使用 `@app.query_param()` 装饰器来验证请求参数的例子:


from fastapi import FastAPI, Query, HTTPException

app = FastAPI()

@app.get("/items/")
def read_items(skip: int = 0, limit: int = 100):
    if limit > 100:
        raise HTTPException(
            status_code=400,
            detail="limit should be less than or equal to 100"
        )
    return {"skip": skip, "limit": limit}

这个例子中,我们定义了两个请求参数 `skip` 和 `limit` ,并使用了 `if` 语句来验证它们。如果 limit > 100,则会抛出一个 HTTPException 异常,并返回一个 HTTP 状态码 400 和一条错误信息 "limit should be less than or equal to 100"。

也可以自定义验证函数,并使用装饰器来验证请求参数


from fastapi import FastAPI, Query, HTTPException

app = FastAPI()

def is_valid_limit(value: int):
    if value > 100:
        raise ValueError("limit should be less than or equal to 100")
    return value

@app.get("/items/")
def read_items(skip: int = 0, limit: int = Query(100, gt=0, lt=100)):
    return {"skip": skip, "limit": limit}

这里我们定义了一个自定义验证函数is_valid_limit,并使用了`@app.query_param(validate=is_valid_limit)` 来验证请求参数 limit。

还可以通过使用第三方库来进行验证,例如:`marshmallow`, `cerberus`等。