| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455 | # (c) Nelen & Schuurmansfrom typing import Optionalfrom typing import Typefrom typing import TypeVarfrom pydantic import BaseModelfrom pydantic import ConfigDictfrom pydantic import ValidationErrorfrom .exceptions import BadRequestfrom .types import Id__all__ = ["ValueObject", "ValueObjectWithId"]T = TypeVar("T", bound="ValueObject")class ValueObject(BaseModel):    model_config = ConfigDict(frozen=True)    def run_validation(self: T) -> T:        try:            return self.__class__(**self.model_dump())        except ValidationError as e:            raise BadRequest(e)    @classmethod    def create(cls: Type[T], **values) -> T:        try:            return cls(**values)        except ValidationError as e:            raise BadRequest(e)    def update(self: T, **values) -> T:        try:            return self.__class__(**{**self.model_dump(), **values})        except ValidationError as e:            raise BadRequest(e)    def __hash__(self):        return hash(self.__class__) + hash(tuple(self.__dict__.values()))K = TypeVar("K", bound="ValueObjectWithId")class ValueObjectWithId(ValueObject):    id: Optional[Id] = None    def update(self: K, **values) -> K:        if "id" in values and self.id is not None and values["id"] != self.id:            raise ValueError("Cannot change the id")        return super().update(**values)
 |