-
Notifications
You must be signed in to change notification settings - Fork 125
Open
Description
Hi,
I am having an issue similar to 117
I am using django-treebeard for hierarchical data in DB and deleting an item with descendants should also delete all related descendants. I also want these items to be safely deleted so policy is SOFT_DELETE_CASCADE
.
I think I am using the treebeard and safedelete packages in the right way but if you see anything wrong with it please do tell:
Note: The models are slightly different but this is how it is basically.
class FolderQuerySet(MP_NodeQuerySet, SafeDeleteQueryset):
pass
class Folder(MP_Node, SafeDeleteModel):
...
objects = SafeDeleteManager.from_queryset(FolderQuerySet)()
all_objects = SafeDeleteAllManager.from_queryset(FolderQuerySet)()
deleted_objects = SafeDeleteDeletedManager.from_queryset(FolderQuerySet)()
When I try to delete a folder,
- it first finds all descendants
- then should safe delete all items and cascade.
But in theSafeDeleteQueryset
on line 66 it calls_, delete_response = obj.delete(force_policy=force_policy)
and this causes the mp_node delete call and starts infinite recursion.
Updating the line with_, delete_response = obj._delete(force_policy=force_policy)
should fix this, right?
class SafeDeleteQueryset(query.QuerySet):
...
def delete(self, force_policy: Optional[int] = None) -> Tuple[int, Dict[str, int]]:
"""Overrides bulk delete behaviour.
.. note::
The current implementation loses performance on bulk deletes in order
to safely delete objects according to the deletion policies set.
.. seealso::
:py:func:`safedelete.models.SafeDeleteModel.delete`
"""
assert self.query.can_filter(), "Cannot use 'limit' or 'offset' with delete."
if force_policy == NO_DELETE:
return (0, {})
elif force_policy == HARD_DELETE:
return self.hard_delete_policy_action()
else:
deleted_counter: Counter = Counter()
# TODO: Replace this by bulk update if we can
for obj in self.all():
_, delete_response = obj.delete(force_policy=force_policy)
deleted_counter.update(delete_response)
self._result_cache = None
return sum(deleted_counter.values()), dict(deleted_counter)
Metadata
Metadata
Assignees
Labels
No labels