I have two models, Schemes and Buildings, where each Building instance belongs to a particular Scheme instance. And the URLs are set up like this:
urlpatterns += [
path('scheme/<uuid:pk>/buildings/', BuildingListView.as_view(), name='building-list'),
path('scheme/<uuid:pk2>/building/<uuid:pk>/', BuildingDetailView.as_view(), name='building-detail'),
path('scheme/<uuid:pk>/buildings/add/', BuildingCreateView.as_view(), name='create-building'),
path('scheme/<uuid:pk2>/building/<uuid:pk>/edit/', BuildingUpdateView.as_view(), name='update-building'),
path('scheme/<uuid:pk2>/building/<uuid:pk>/delete/', BuildingDeleteView.as_view(), name='delete-building'),
]
I created my delete view so that it will redirect to the first URL in the above list (‘building-list’). However, this need the pk of the Building instance, which is tied to the object being deleted.
I’ve come across multiple options while searching for a solution, and those included:
- Overriding a method called ‘delete( )’ of the DeleteView
- Using the init() to save the required pk before the item gets deleted
- Workarounds inside the get_success_url method itself, using kwargs or object
- And a few other that I didn’t understand at all…
None worked, and the issue appeared to be still tied to get_success_url getting executed after the object was deleted. (although, I don’t think I did the delete( ) method workaround correctly).
However, after some fiddling around, I thought of calling the get_success_url inside the form_valid before the object is deleted, and save it there. And then the view worked. This is my DeleteView right now:
class BuildingDeleteView(PermissionRequiredMixin, DeleteView):
model = Building
permission_required = 'components.delete_building'
def form_valid(self, form):
try:
success_url = self.get_success_url()
self.object.delete()
return HttpResponseRedirect(success_url)
except Exception as e:
return HttpResponseRedirect(
reverse_lazy('schemes:delete-building', kwargs={'pk2': self.object.scheme.pk, 'pk': self.object.pk})
)
def get_success_url(self, **kwargs) -> str:
scheme = self.get_object().scheme
return reverse_lazy('schemes:building-list', kwargs={'pk': scheme.id})
What I would like to know is, if I’m doing something incorrect here, or if there’s something that might result in some other bug in a scenario which I’m unware of.
Any help or recommendations on the correctness of the above, or if not, the best convention to handle a similar situation is much appreciated.