Misc cleanup

This commit is contained in:
Jeremy Stretch 2023-11-01 11:29:09 -04:00
parent ee5be84911
commit 593fa468a5
2 changed files with 42 additions and 35 deletions

View File

@ -324,7 +324,8 @@ class ObjectDeleteView(GetReturnURLMixin, BaseObjectView):
def _get_dependent_objects(self, obj): def _get_dependent_objects(self, obj):
""" """
Returns a dict of dependent objects, model names as primary key, inside each two keys exist title and objects (list) Returns a dictionary mapping of dependent objects (organized by model) which will be deleted as a result of
deleting the requested object.
Args: Args:
obj: The object to return dependent objects for obj: The object to return dependent objects for
@ -332,18 +333,15 @@ class ObjectDeleteView(GetReturnURLMixin, BaseObjectView):
using = router.db_for_write(obj._meta.model) using = router.db_for_write(obj._meta.model)
collector = Collector(using=using) collector = Collector(using=using)
collector.collect([obj]) collector.collect([obj])
related_objects = defaultdict(dict)
# Compile a mapping of models to instances
dependent_objects = defaultdict(list)
for model, instance in collector.instances_with_model(): for model, instance in collector.instances_with_model():
if instance == obj: # Omit the root object
continue if instance != obj:
dependent_objects[model].append(instance)
related_objects.setdefault(model.__name__, {"objects": []})['objects'].append(instance) return dict(dependent_objects)
if len(related_objects[model.__name__]['objects']) == 1:
related_objects[model.__name__]['title'] = title(model._meta.verbose_name)
else:
related_objects[model.__name__]['title'] = title(model._meta.verbose_name_plural)
return dict(related_objects)
# #
# Request handlers # Request handlers
@ -358,8 +356,7 @@ class ObjectDeleteView(GetReturnURLMixin, BaseObjectView):
""" """
obj = self.get_object(**kwargs) obj = self.get_object(**kwargs)
form = ConfirmationForm(initial=request.GET) form = ConfirmationForm(initial=request.GET)
dependent_objects = self._get_dependent_objects(obj)
related_objects = self._get_dependent_objects(obj)
# If this is an HTMX request, return only the rendered deletion form as modal content # If this is an HTMX request, return only the rendered deletion form as modal content
if is_htmx(request): if is_htmx(request):
@ -370,7 +367,7 @@ class ObjectDeleteView(GetReturnURLMixin, BaseObjectView):
'object_type': self.queryset.model._meta.verbose_name, 'object_type': self.queryset.model._meta.verbose_name,
'form': form, 'form': form,
'form_url': form_url, 'form_url': form_url,
'related_objects': related_objects, 'dependent_objects': dependent_objects,
**self.get_extra_context(request, obj), **self.get_extra_context(request, obj),
}) })
@ -378,7 +375,7 @@ class ObjectDeleteView(GetReturnURLMixin, BaseObjectView):
'object': obj, 'object': obj,
'form': form, 'form': form,
'return_url': self.get_return_url(request, obj), 'return_url': self.get_return_url(request, obj),
'related_objects': related_objects, 'dependent_objects': dependent_objects,
**self.get_extra_context(request, obj), **self.get_extra_context(request, obj),
}) })

View File

@ -12,29 +12,39 @@
Are you sure you want to <strong class="text-danger">delete</strong> {{ object_type }} <strong>{{ object }}</strong>? Are you sure you want to <strong class="text-danger">delete</strong> {{ object_type }} <strong>{{ object }}</strong>?
{% endblocktrans %} {% endblocktrans %}
</p> </p>
{% if related_objects %} {% if dependent_objects %}
<p> <p>
This will cause deletion of the following objects: <br> {% trans "The following objects will be deleted as a result of this action." %}
</p>
<div class="accordion" id="deleteAccordion"> <div class="accordion" id="deleteAccordion">
{% for model, instances in dependent_objects.items %}
{% for model,object_dict in related_objects.items %} <div class="accordion-item">
<div class="accordion-item"> <h2 class="accordion-header" id="deleteheading{{ forloop.counter }}">
<h2 class="accordion-header" id="deleteheading{{ forloop.counter }}"> <button class="accordion-button collapsed" type="button" data-bs-toggle="collapse" data-bs-target="#collapse{{ forloop.counter }}" aria-expanded="false" aria-controls="collapse{{ forloop.counter }}">
<button class="accordion-button collapsed" type="button" data-bs-toggle="collapse" data-bs-target="#collapse{{ forloop.counter }}" aria-expanded="false" aria-controls="collapse{{ forloop.counter }}"> {% with object_count=instances|length %}
{{ object_dict.objects |length }} {{ object_dict.title }} {{ object_count }}
</button> {% if object_count == 1 %}
</h2> {{ model|meta:"verbose_name" }}
<div id="collapse{{ forloop.counter }}" class="accordion-collapse collapse" aria-labelledby="deleteheading{{ forloop.counter }}" data-bs-parent="#deleteAccordion"> {% else %}
<div class="accordion-body"> {{ model|meta:"verbose_name_plural" }}
{% for object in object_dict.objects %} {% endif %}
- {{ object | linkify }}{% if not forloop.last %}<br> {% endif %} {% endwith %}
{% endfor %} </button>
</h2>
<div id="collapse{{ forloop.counter }}" class="accordion-collapse collapse" aria-labelledby="deleteheading{{ forloop.counter }}" data-bs-parent="#deleteAccordion">
<div class="accordion-body p-0">
<div class="list-group list-group-flush">
{% for instance in instances %}
{% with url=instance.get_absolute_url %}
<a {% if url %}href="{{ url }}" {% endif %}class="list-group-item list-group-item-action">{{ instance }}</a>
{% endwith %}
{% endfor %}
</div>
</div>
</div> </div>
</div> </div>
</div> {% endfor %}
{% endfor %} </div>
</div>
</p>
{% endif %} {% endif %}
{% render_form form %} {% render_form form %}
</div> </div>