Привет.
Есть вот такая модель категории товаров.
Модель Category
class Category(MPTTModel):
name = models.CharField(max_length=50)
slug = models.SlugField(allow_unicode=True, db_index=True)
parent = TreeForeignKey(
"self",
on_delete=models.CASCADE,
null=True,
blank=True,
related_name="children"
)
В каждом шаблоне делаю доступной переменную categories, в которую помещаю все категории из бд через контекстный процессор:
Контекстный процессор
def categories(_: HttpRequest) -> dict[str, Any]:
return {
"categories": Category.objects.all(),
}
В шаблоне каталога товаров (в сайдбаре) есть вот такой код (делал по примеру из документации), который выводит полностью всё дерево:
Шаблон
{% if categories %}
<section class="sidebar-section sidebar__section">
<div class="sidebar-section__title">
Категории товаров
</div>
<div class="category-nav">
<ul class="category-nav__list">
{% recursetree categories %}
<li class="category-nav__item">
<a class="category-nav__link" href="{{ node.get_absolute_url }}">
{{ node.name }}
</a>
{% if not node.is_leaf_node %}
<button class="category-nav__btn" type="button">
<svg xmlns="http://www.w3.org/2000/svg" width="11" height="6" fill="none" viewBox="0 0 11 6">
<path stroke="#2E2E2E" stroke-linecap="round" stroke-linejoin="round" d="m1 1 4.456 4.386L9.914 1" />
</svg>
</button>
<div class="category-nav category-nav--sub">
<ul class="category-nav__list">
{{ children }}
</ul>
</div>
{% endif %}
</li>
{% endrecursetree %}
</ul>
</div>
</section>
{% endif %}
И примерно такой же код есть в шапке, чтобы вывести все категории в навигации.
Когда захожу на страницу каталога (где есть сайдбар с категориями), в таблицу с категориями идет 7 запросов. Если закомменчу сайдбар, то будет 4 запроса. Но почему? И на другие страницы, где нет сайдбара с категориями я захожу, там тоже запросов меньше.
То есть когда 2 раза вывожу одно и тоже дерево он почему-то делает больше запросов. Но ведь я один раз получил все категории в контекстном процессоре. Трудность еще в том, что я не знаю алгоритм Nested Set, который используется в этой библиотеке и подумал, может кто подскажет здесь, нормальная ли у меня ситуация. Сколько должно быть запросов для вывода всего дерева?
UPD: я тут посмотрел, что запросы дублируются: 1 запрос идет из контекстного процессора на получение всех категорий.
3 запроса для вывода дерева в навигации и 3 запроса для вывода в сайдбаре. Если сайдбара нет, то минус 3 запроса.
Вот сами запросы, вывел в шаблоне через переменную sql_queries:
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC 0.002
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" WHERE "shop_category"."id" = 3 ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC 0.001
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" WHERE "shop_category"."id" = 1 ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC 0.001
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" WHERE "shop_category"."id" = 2 ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC 0.001
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" WHERE "shop_category"."id" = 3 ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC 0.001
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" WHERE "shop_category"."id" = 1 ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC 0.001
SELECT "shop_category"."id", "shop_category"."name", "shop_category"."slug", "shop_category"."parent_id", "shop_category"."lft", "shop_category"."rght", "shop_category"."tree_id", "shop_category"."level" FROM "shop_category" WHERE "shop_category"."id" = 2 ORDER BY "shop_category"."tree_id" ASC, "shop_category"."lft" ASC