Есть задача вывести 50 000 сотрудников в иерархическом порядке на веб страницу Django.
Столько записей страница вывести не в состоянии, поэтому решил сделать пагинацию.
Но проблема в том, что у меня всего один объект - главный работник (Ashley Roberts), уже у которого есть подчиненные, и которые выводятся в шаблоне через итерацию этого самого единственного работника.
Возможно как-то сделать пагинацию для обьектов, которые выводятся через цикл?
Или возможно я зашел не с той стороны решения задачи, как тогда будет правильнее сделать?
Выглядит это так:
models.py
class Employee(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=100)
email = models.EmailField(null=True)
hire_date = models.DateField(default=timezone.now)
position = models.CharField(max_length=100)
parent = models.ForeignKey('self', on_delete=models.CASCADE, null=True, blank=True, related_name='subordinates')
def __str__(self):
return self.name
view.py
def index(request):
employees = Employee.objects.all()
# print("qyery: ", employees)
employees = [i for i in employees]
# print("Employees:", employees)
# return employees list that shoul remove from iteration
def clear_employers():
parent_id_list = [i.parent_id for i in employees] # [None, 1087, 1087]
id_list = [i.id for i in employees] # [1087, 1088, 1089]
parent_id_equil_id = [id for id in parent_id_list if id in id_list] # [1087, 1087]
clear_workers = [] # workers that should remove for unrepeating in iteration in template
for i, worker in enumerate(employees):
# print(i, " | ", worker, " | ", worker.parent_id)
if worker.parent_id in parent_id_equil_id:
clear_workers.append(worker)
#print("worker to remove:", worker.name)
#print("clear_workers ****", clear_workers)
return clear_workers
# function that compare two lists and return list of needed employees
def compare(*args):
employees_res = [e for e in employees if e not in clear_employers()]
return employees_res
employees = compare(employees, clear_employers())
print(employees)
print("Change Employees:", len([subordinates_employees for subordinates_employees in employees]))
paginator = Paginator(employees, 200)
page_number = request.GET.get('page')
page_obj = paginator.get_page(page_number)
return render(request, "page/index.html", {'page_obj': page_obj})
html. Здесь семь вложенных циклов потому что иерархия из семи звеньев
{% block content %}
<center>
<p class="h1">Hierarchy of workers</p>
</center>
<ul class="list-group m-2">
{% for employee in page_obj %}
<a class="list-group-item list-group-item-danger dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ employee.name }} - {{ employee.position }}</a>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Manager: {{ employee.parent }}</a></li>
<li><a class="dropdown-item" href="#">{{ employee.email }}</a></li>
<li><a class="dropdown-item" href="#">Hiring date: {{ employee.hire_date }}</a></li>
</ul>
{% if employee.subordinates.all %}
<ul>
{% for sub_1 in employee.subordinates.all %}
<a class="list-group-item list-group-item-warning dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ sub_1.name }} - {{ sub_1.position }}</a>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Manager: {{ sub_1.parent }}</a></li>
<li><a class="dropdown-item" href="#">{{ sub_1.email }}</a></li>
<li><a class="dropdown-item" href="#">Hiring date: {{ sub_1.hire_date }}</a></li>
</ul>
{% if sub_1.subordinates.all %}
<ul class="">
{% for sub_2 in sub_1.subordinates.all %}
<a class="list-group-item list-group-item-info dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ sub_2.name }} - {{ sub_2.position }}</a>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Manager: {{ sub_2.parent }}</a></li>
<li><a class="dropdown-item" href="#">{{ sub_2.email }}</a></li>
<li><a class="dropdown-item" href="#">Hiring date: {{ sub_2.hire_date }}</a></li>
</ul>
{% if sub_2.subordinates.all %}
<ul class="">
{% for sub_3 in sub_2.subordinates.all %}
<a class="list-group-item list-group-item-success dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ sub_3.name }} - {{ sub_3.position }}</a>
{% if sub_3.subordinates.all %}
<ul class="">
{% for sub_4 in sub_3.subordinates.all %}
<a class="list-group-item list-group-item-primary dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ sub_4.name }} - {{ sub_4.position }}</a>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Manager: {{ sub_4.parent }}</a></li>
<li><a class="dropdown-item" href="#">{{ sub_4.email }}</a></li>
<li><a class="dropdown-item" href="#">Hiring date: {{ sub_4.hire_date }}</a></li>
</ul>
{% if sub_4.subordinates.all %}
<ul class="">
{% for sub_5 in sub_4.subordinates.all %}
<a class="list-group-item list-group-item-dark dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ sub_5.name }} - {{ sub_5.position }}</a>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Manager: {{ sub_5.parent }}</a></li>
<li><a class="dropdown-item" href="#">{{ sub_5.email }}</a></li>
<li><a class="dropdown-item" href="#">Hiring date: {{ sub_5.hire_date }}</a></li>
</ul>
{% if sub_5.subordinates.all %}
<ul class="">
{% for sub_6 in sub_5.subordinates.all %}
<a class="list-group-item list-group-item-light dropdown-toggle" href="#" role="button" data-bs-toggle="dropdown" aria-expanded="false">{{ sub_6.name }} - {{ sub_6.position }}</a>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Manager: {{ sub_6.parent }}</a></li>
<li><a class="dropdown-item" href="#">{{ sub_6.email }}</a></li>
<li><a class="dropdown-item" href="#">Hiring date: {{ sub_6.hire_date }}</a></li>
</ul>
{% endfor %}
</ul>
{% endif %}
{% endfor %}
</ul>
{% endif %}
{% endfor %}
</ul>
{% endif %}
{% endfor %}
</ul>
{% endif %}
{% endfor %}
</ul>
{% endif %}
</li>
{% endfor %}
{% endif %}
{% endfor %}
</ul>
</ul>