如何从单个SQLAlchemy对象生成Pydantic嵌套结构?
如何从SQLAlchemy对象生成Pydantic嵌套属性
问题背景
现有SQLAlchemy模型:
class FooORM(BaseORM): __tablename__ = 'foo' id = Column(Integer) cost_high = Column(Integer) cost_low = Column(Integer)
对应的初始Pydantic模型:
from pydantic import BaseModel, ConfigDict class FooModel(BaseModel): model_config = ConfigDict(from_attributes=True) id: int cost_high: int cost_low: int
当前输出结构:
{"id": 1, "cost_high": 5, "cost_low": 0}
期望输出结构:
{"id": 1, "cost": {"high": 5, "low": 0}}
尝试定义嵌套Cost模型后,无法自动将cost_high映射到Cost.high,需要实现反向的属性嵌套转换。
解决方案
方法1:使用Pydantic v2+的computed_field(简单直观)
通过计算属性动态生成嵌套的cost字段,保留原ORM字段映射的同时生成期望的嵌套结构:
from pydantic import BaseModel, ConfigDict, computed_field class Cost(BaseModel): high: int low: int class FooModel(BaseModel): model_config = ConfigDict(from_attributes=True) id: int cost_high: int cost_low: int @computed_field @property def cost(self) -> Cost: return Cost(high=self.cost_high, low=self.cost_low)
方法2:字段别名映射(隐藏原扁平字段)
如果不需要在FooModel中暴露cost_high和cost_low,可以通过Field的validation_alias直接完成映射:
from pydantic import BaseModel, ConfigDict, Field class Cost(BaseModel): high: int = Field(validation_alias="cost_high") low: int = Field(validation_alias="cost_low") class FooModel(BaseModel): model_config = ConfigDict(from_attributes=True) id: int cost: Cost
方法3:自定义模型验证器(复杂场景适配)
针对多输入类型或复杂转换逻辑,使用model_validator手动处理属性映射:
from pydantic import BaseModel, ConfigDict, model_validator class Cost(BaseModel): high: int low: int class FooModel(BaseModel): model_config = ConfigDict(from_attributes=True) id: int cost: Cost @model_validator(mode="before") def unpack_cost_fields(cls, values): # 适配ORM对象输入 if isinstance(values, FooORM): return { "id": values.id, "cost": {"high": values.cost_high, "low": values.cost_low} } # 适配字典输入 values["cost"] = { "high": values.pop("cost_high"), "low": values.pop("cost_low") } return values
内容的提问来源于stack exchange,提问作者PGHE
相关产品推荐
相关产品推荐

