如何在FastAPI中使用字段别名而不是名称返回Pydantic模型?

4
我的 FastAPI 调用没有按照正确的 Response 模型格式返回数据,它是以数据库模型的格式返回数据。
我的数据库模型:
class cat(DBConnect.Base):
     __tablename__ = 'category'
     __table_args__ = {"schema": SCHEMA}
     cat_id = Column('cat_id',UUID(as_uuid=True), primary_key=True, default=uuid.uuid4)
     cat_desc = Column('cat_desc', TEXT, nullable=True)
     cat_h__l_name = Column('cat_h_l_name', TEXT, nullable=True)

我的Pydantic模型:

class CamelModel(BaseModel):
    class config:
        alias_generator = to_camel
        allow_population_by_field_name = True

class cat(CamelModel):
    cat_id =Field(alais='CatID', readonly=True)
    cat_description =Field(alias='CatDescription')
    cat_h__l_name = Field(alias='CatName')
     
    class config:
       orm_mode= True

我的API调用:

@router.patch('/cat/{id}/', response_model = 'cat')
def update_cat(response= Response, params: updatecat = Depends(updatecat)):
    response_obj = { resonse_code: status.HTTP_200_OK, 
    response_obj : {}    
    }
    
    response_obj = session.query() # It is returning the correct data from the database
    response.status_code = response_obj['response_code']
    
    return JSONResponse(response_obj['response_obj'], status_code = response_obj['response_code'])

获取以下格式的响应:
     cat_id = 'some uuid'
     cat_desc = 'desc'
     cat_h__l_name = 'some h_l_name'

但我希望响应的格式如下:

CatID = 'some uuid'
CatDescription ='' some description'
CatName = 'Some cat name'

这段代码没有报错(我已经打过了,所以可能存在一些缩进或拼写错误)。唯一的问题是API没有返回正确的数据格式。我已经卡在这里一段时间了。我对FastAPI还很陌生,请帮帮我。

1个回答

4
你可以在端点中添加response_model_by_alias=True。这在文档中这里提到了。
from fastapi import FastAPI
from pydantic import BaseModel

app = FastAPI()


def to_camel(string: str) -> str:
    return ''.join(word.capitalize() for word in string.split('_'))

class Item(BaseModel):
    name: str
    language_code: str
    
    class Config:
        alias_generator = to_camel
        allow_population_by_field_name = True    
            

fake_db = [
    Item(name='foo', language_code='en'),
    Item(name='bar', language_code='fr')
]


@app.get('/item/{item_id}', response_model=Item, response_model_by_alias=True)
def create_item(item_id: int):
    return fake_db[item_id]

然而,由于您在端点中返回的是JSONResponse而不是模型,因此设置response_model_by_alias=True将没有任何效果。因此,您可以将模型转换为字典,使用Pydantic的model.dict(...)注意,该方法现已被model.model_dump(...)替代),并将by_alias参数设置为True

顺便提一句,如果您有一个 Pydantic 模型,在将其放入 JSONResponse 之前,必须先将其转换为 dict。如果您有数据类型,例如 datetimeUUID 等无法序列化的情况,您可以使用 jsonable_encoder 将数据转换为响应前进行处理。jsonable_encoder 将确保无法序列化的对象被转换为 str

from fastapi.responses import JSONResponse
from fastapi.encoders import jsonable_encoder

@app.get('/item/{item_id}')
def create_item(item_id: int):
    return JSONResponse(jsonable_encoder(fake_db[item_id].dict(by_alias=True)), status_code=200)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接