add saving status and basic test for this
This commit is contained in:
@ -42,13 +42,13 @@ class Model(NewBaseModel):
|
||||
|
||||
@classmethod
|
||||
def from_row( # noqa CCR001
|
||||
cls: Type[T],
|
||||
row: sqlalchemy.engine.ResultProxy,
|
||||
select_related: List = None,
|
||||
related_models: Any = None,
|
||||
previous_table: str = None,
|
||||
fields: Optional[Union[Dict, Set]] = None,
|
||||
exclude_fields: Optional[Union[Dict, Set]] = None,
|
||||
cls: Type[T],
|
||||
row: sqlalchemy.engine.ResultProxy,
|
||||
select_related: List = None,
|
||||
related_models: Any = None,
|
||||
previous_table: str = None,
|
||||
fields: Optional[Union[Dict, Set]] = None,
|
||||
exclude_fields: Optional[Union[Dict, Set]] = None,
|
||||
) -> Optional[T]:
|
||||
|
||||
item: Dict[str, Any] = {}
|
||||
@ -58,9 +58,9 @@ class Model(NewBaseModel):
|
||||
related_models = group_related_list(select_related)
|
||||
|
||||
if (
|
||||
previous_table
|
||||
and previous_table in cls.Meta.model_fields
|
||||
and issubclass(cls.Meta.model_fields[previous_table], ManyToManyField)
|
||||
previous_table
|
||||
and previous_table in cls.Meta.model_fields
|
||||
and issubclass(cls.Meta.model_fields[previous_table], ManyToManyField)
|
||||
):
|
||||
previous_table = cls.Meta.model_fields[
|
||||
previous_table
|
||||
@ -90,20 +90,23 @@ class Model(NewBaseModel):
|
||||
exclude_fields=exclude_fields,
|
||||
)
|
||||
|
||||
instance: Optional[T] = cls(**item) if item.get(
|
||||
cls.Meta.pkname, None
|
||||
) is not None else None
|
||||
if item.get(cls.Meta.pkname, None) is not None:
|
||||
instance: Optional[T] = cls(**item)
|
||||
instance.set_save_status(True)
|
||||
else:
|
||||
instance = None
|
||||
|
||||
return instance
|
||||
|
||||
@classmethod
|
||||
def populate_nested_models_from_row( # noqa: CFQ002
|
||||
cls,
|
||||
item: dict,
|
||||
row: sqlalchemy.engine.ResultProxy,
|
||||
related_models: Any,
|
||||
previous_table: sqlalchemy.Table,
|
||||
fields: Optional[Union[Dict, Set]] = None,
|
||||
exclude_fields: Optional[Union[Dict, Set]] = None,
|
||||
cls,
|
||||
item: dict,
|
||||
row: sqlalchemy.engine.ResultProxy,
|
||||
related_models: Any,
|
||||
previous_table: sqlalchemy.Table,
|
||||
fields: Optional[Union[Dict, Set]] = None,
|
||||
exclude_fields: Optional[Union[Dict, Set]] = None,
|
||||
) -> dict:
|
||||
for related in related_models:
|
||||
if isinstance(related_models, dict) and related_models[related]:
|
||||
@ -137,12 +140,12 @@ class Model(NewBaseModel):
|
||||
|
||||
@classmethod
|
||||
def extract_prefixed_table_columns( # noqa CCR001
|
||||
cls,
|
||||
item: dict,
|
||||
row: sqlalchemy.engine.result.ResultProxy,
|
||||
table_prefix: str,
|
||||
fields: Optional[Union[Dict, Set]] = None,
|
||||
exclude_fields: Optional[Union[Dict, Set]] = None,
|
||||
cls,
|
||||
item: dict,
|
||||
row: sqlalchemy.engine.result.ResultProxy,
|
||||
table_prefix: str,
|
||||
fields: Optional[Union[Dict, Set]] = None,
|
||||
exclude_fields: Optional[Union[Dict, Set]] = None,
|
||||
) -> dict:
|
||||
|
||||
# databases does not keep aliases in Record for postgres, change to raw row
|
||||
@ -179,6 +182,7 @@ class Model(NewBaseModel):
|
||||
item_id = await self.Meta.database.execute(expr)
|
||||
if item_id: # postgress does not return id if it's already there
|
||||
setattr(self, self.Meta.pkname, item_id)
|
||||
self.set_save_status(True)
|
||||
return self
|
||||
|
||||
async def update(self: T, **kwargs: Any) -> T:
|
||||
@ -193,12 +197,14 @@ class Model(NewBaseModel):
|
||||
expr = expr.where(self.pk_column == getattr(self, self.Meta.pkname))
|
||||
|
||||
await self.Meta.database.execute(expr)
|
||||
self.set_save_status(True)
|
||||
return self
|
||||
|
||||
async def delete(self: T) -> int:
|
||||
expr = self.Meta.table.delete()
|
||||
expr = expr.where(self.pk_column == (getattr(self, self.Meta.pkname)))
|
||||
result = await self.Meta.database.execute(expr)
|
||||
self.set_save_status(False)
|
||||
return result
|
||||
|
||||
async def load(self: T) -> T:
|
||||
@ -211,4 +217,5 @@ class Model(NewBaseModel):
|
||||
kwargs = dict(row)
|
||||
kwargs = self.translate_aliases_to_columns(kwargs)
|
||||
self.from_dict(kwargs)
|
||||
self.set_save_status(True)
|
||||
return self
|
||||
|
||||
@ -220,6 +220,7 @@ class ModelTableProxy:
|
||||
field,
|
||||
cls.merge_two_instances(current_field, getattr(other, field)),
|
||||
)
|
||||
other.set_save_status(True)
|
||||
return other
|
||||
|
||||
@staticmethod
|
||||
|
||||
@ -123,12 +123,16 @@ class NewBaseModel(
|
||||
object.__setattr__(self, name, value)
|
||||
elif name == "pk":
|
||||
object.__setattr__(self, self.Meta.pkname, value)
|
||||
self.set_save_status(False)
|
||||
elif name in self._orm:
|
||||
model = self.Meta.model_fields[name].expand_relationship(value, self)
|
||||
if isinstance(self.__dict__.get(name), list):
|
||||
# virtual foreign key or many to many
|
||||
self.__dict__[name].append(model)
|
||||
else:
|
||||
# foreign key relation
|
||||
self.__dict__[name] = model
|
||||
self.set_save_status(False)
|
||||
else:
|
||||
value = (
|
||||
self._convert_json(name, value, "dumps")
|
||||
@ -136,15 +140,16 @@ class NewBaseModel(
|
||||
else value
|
||||
)
|
||||
super().__setattr__(name, value)
|
||||
self.set_save_status(False)
|
||||
|
||||
def __getattribute__(self, item: str) -> Any:
|
||||
if item in (
|
||||
"_orm_id",
|
||||
"_orm_saved",
|
||||
"_orm",
|
||||
"__fields__",
|
||||
"_related_names",
|
||||
"_props",
|
||||
"_orm_id",
|
||||
"_orm_saved",
|
||||
"_orm",
|
||||
"__fields__",
|
||||
"_related_names",
|
||||
"_props",
|
||||
):
|
||||
return object.__getattribute__(self, item)
|
||||
if item == "pk":
|
||||
@ -158,7 +163,7 @@ class NewBaseModel(
|
||||
return super().__getattribute__(item)
|
||||
|
||||
def _extract_related_model_instead_of_field(
|
||||
self, item: str
|
||||
self, item: str
|
||||
) -> Optional[Union["T", Sequence["T"]]]:
|
||||
# alias = self.get_column_alias(item)
|
||||
if item in self._orm:
|
||||
@ -172,9 +177,9 @@ class NewBaseModel(
|
||||
|
||||
def __same__(self, other: "NewBaseModel") -> bool:
|
||||
return (
|
||||
self._orm_id == other._orm_id
|
||||
or self.dict() == other.dict()
|
||||
or (self.pk == other.pk and self.pk is not None)
|
||||
self._orm_id == other._orm_id
|
||||
or self.dict() == other.dict()
|
||||
or (self.pk == other.pk and self.pk is not None)
|
||||
)
|
||||
|
||||
@classmethod
|
||||
@ -199,11 +204,14 @@ class NewBaseModel(
|
||||
def remove(self, name: "T") -> None:
|
||||
self._orm.remove_parent(self, name)
|
||||
|
||||
def set_save_status(self, status: bool) -> None:
|
||||
object.__setattr__(self, "_orm_saved", status)
|
||||
|
||||
@classmethod
|
||||
def get_properties(
|
||||
cls,
|
||||
include: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
exclude: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
cls,
|
||||
include: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
exclude: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
) -> List[str]:
|
||||
if isinstance(cls._props, list):
|
||||
props = cls._props
|
||||
@ -212,7 +220,7 @@ class NewBaseModel(
|
||||
prop
|
||||
for prop in dir(cls)
|
||||
if isinstance(getattr(cls, prop), property)
|
||||
and prop not in ("__values__", "__fields__", "fields", "pk_column")
|
||||
and prop not in ("__values__", "__fields__", "fields", "pk_column")
|
||||
]
|
||||
cls._props = props
|
||||
if include:
|
||||
@ -222,16 +230,16 @@ class NewBaseModel(
|
||||
return props
|
||||
|
||||
def dict( # noqa A003
|
||||
self,
|
||||
*,
|
||||
include: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
exclude: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
by_alias: bool = False,
|
||||
skip_defaults: bool = None,
|
||||
exclude_unset: bool = False,
|
||||
exclude_defaults: bool = False,
|
||||
exclude_none: bool = False,
|
||||
nested: bool = False
|
||||
self,
|
||||
*,
|
||||
include: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
exclude: Union["AbstractSetIntStr", "MappingIntStrAny"] = None,
|
||||
by_alias: bool = False,
|
||||
skip_defaults: bool = None,
|
||||
exclude_unset: bool = False,
|
||||
exclude_defaults: bool = False,
|
||||
exclude_none: bool = False,
|
||||
nested: bool = False
|
||||
) -> "DictStrAny": # noqa: A003'
|
||||
dict_instance = super().dict(
|
||||
include=include,
|
||||
|
||||
Reference in New Issue
Block a user