Pydantic BaseModel 类实例化后更改字段

Jiv*_*van 20 python python-3.x pydantic

对于如下 Pydantic 类,我想foo通过应用replace操作来转换字段:

from typing import List
from pydantic import BaseModel

class MyModel(BaseModel):
    foo: List[str]

my_object = MyModel(foo="hello-there")
my_object.foo = [s.replace("-", "_") for s in my_object.foo]
Run Code Online (Sandbox Code Playgroud)

创建对象时,如何replace在类中正确执行操作?如果没有 Pydantic,我会简单地在其中执行此操作__init(self, foo),但由于 Pydantic 创建了自己的__init__实现,我不确定如何准确地进行。

tbj*_*rch 28

使用 pydantic BaseModel

看来您必须重写 basemodels init 方法,如下所示:

from typing import List
from pydantic import BaseModel

class MyModel(BaseModel):
    foo: List[str]

    def __init__(self, **data):
        data["foo"] = [s.replace("-", "_") for s in data["foo"]]
        super().__init__(**data)

my_object = MyModel(foo=["hello-there"])

print(my_object)
# Outputs foo=['hello_there']
Run Code Online (Sandbox Code Playgroud)

使用 Pydantic 数据类

...或者您也可以将其转换为 pydantic 数据类,并使用 pydantic 提供的 post init dunder 在实例化时执行其他操作。例如:

from typing import List
from pydantic.dataclasses import dataclass

@dataclass
class MyModel():
    foo: List[str]

    def __post_init__(self):
        self.foo = [s.replace("-", "_") for s in self.foo]

my_object = MyModel(foo=["hello-there"])

print(my_object)

# Outputs foo=['hello_there']
Run Code Online (Sandbox Code Playgroud)


Ita*_*ski 17

派丹蒂克版本 2.0+

根据文档,语法如下:

class MyModel(BaseModel):
    a: int
    b: str
    
    def model_post_init(self, __context) -> None:
        values = self.dict()
        # manipulation on fields
Run Code Online (Sandbox Code Playgroud)


Sac*_*cha 16

使用@validator装饰器(在本例中使用选项each_item=True,因为我们希望验证器查看列表中的每个项目而不是列表本身):

from typing import List
from pydantic import BaseModel, validator

class MyModel(BaseModel):
    foo: List[str]

    @validator('foo', each_item=True)
    def replace_hyphen(cls,v):
        return v.replace("-","_")

my_object = MyModel(foo=["hello-there"])

print(my_object)
# Outputs foo=['hello_there']
Run Code Online (Sandbox Code Playgroud)

或者如果您更喜欢数据类:

from typing import List
from pydantic import validator
from pydantic.dataclasses import dataclass

@dataclass
class MyModelDC():
    foo: List[str]

    @validator('foo', each_item=True)
    def replace_hyphen(cls,v):
        return v.replace("-","_")

my_objectDC = MyModelDC(foo=["hello-there"])

print(my_objectDC)
# Outputs foo=['hello_there']
Run Code Online (Sandbox Code Playgroud)