{# Список проектов по бизнесам — переиспользуемый партиал (Все проекты + страница бизнеса). Контекст: d (overview/business-срез), csrf, write_blocked. Стили блока — в head страницы. #} {% import "_project_pulse_macros.html" as pp %} {% set s = d.stats %} {% set fc = d.facets %} {# colspan вложенной строки планов — должен совпадать с реальным числом ниже. #} {% set pp_colcount = 6 if (csrf and not write_blocked) else 5 %} {% set pp_groups_with_projects = d.business_groups | selectattr('projects') | list %} {% if s.done and not fc.active.statuses %}
{% if d.done_hidden %} 👁 Показать готовые ({{ s.done }}) {% else %} {# show_done=1 активен → список показывает ТОЛЬКО готовые+архив; ссылка снимает параметр и возвращает обычный вид (готовые снова скрыты). #} ← Назад к активным {% endif %}
{% endif %} {% if pp_groups_with_projects %}
{% endif %} {% for g in d.business_groups %}
{{ g.label }} {{ g.projects|length }} проект(ов){% if g.queued_ideas %} · {{ g.queued_ideas|length }} идей в работе 💡{% endif %}{% if g.ideas %} · {{ g.ideas|length }} идей 💡{% endif %}
{% if g.projects or g.queued_ideas %}
{% if csrf and not write_blocked %}{% endif %} {# идеи, перенесённые в бизнес (status=implement) — строкой ПЕРЕД проектами #} {% for i in g.queued_ideas %} {% if csrf and not write_blocked %} {% endif %} {% endfor %} {% for p in g.projects %} {% if csrf and not write_blocked %} {% endif %} {# завершённые = все НЕ-живые планы (done + archived вместе): сдача переносом в plans/done/ даёт archived, поэтому plan_done для счётчика не годится. #} {% set pp_live_plans = p.plans | rejectattr('status', 'in', ['done', 'archived']) | list %} {% set pp_closed_count = p.plans|length - pp_live_plans|length %} {% if pp_live_plans %} {% elif pp_closed_count %} {# живых планов нет, но закрытые есть — одна серая неинтерактивная строка без details и стрелочки (пустой раскрытый блок не рисуем). #} {% endif %} {% endfor %}
Проект Статус Приоритет Готовность Планы
💡 {{ i.title }} идея в работе ● В работе
{{ p.name }} {% if p.ideas %}💡 {{ p.ideas|length }}{% endif %} {{ pp.status_chip(p.status, p.status_ru) }} {{ pp.score_badge(p.score, p.reason) }} {{ p.reason }} {{ pp.progress_bar(p.blocks_done, p.blocks_total, p.blocks_progress, 'is-done' if p.status=='done' else '') }} {{ p.plan_done }}/{{ p.plan_count }} {% if p.status != 'done' %}
{% if p.status != 'archived' %}{% endif %}
{% endif %}
Планы {{ pp_live_plans|length }}
{% for pl in pp_live_plans %}
{% if pl.missing %} {# план залинкован (links:), но файл не резолвится — status_ru уже несёт «нет файла», отдельную дату не дублируем. #} {{ pl.title }} {{ pp.status_chip(pl.status, pl.status_ru) }} {% else %} {{ pl.title }} {% if pl.owner_id and pl.owner_id != g.key %} {{ pl.business }} {% endif %} {{ pp.status_chip(pl.status, pl.status_ru) }} {# гард пустых дат: план без даты в имени файла (date='') не должен давать висящее «создан ». Обе даты пусты → span не рендерим вовсе. #} {% if pl.date and pl.modified and pl.modified != pl.date %} создан {{ pl.date }} · изменён {{ pl.modified }} {% elif pl.date %} создан {{ pl.date }} {% elif pl.modified %} изменён {{ pl.modified }} {% endif %} {% endif %}
{% endfor %} {% if pp_closed_count %}
+{{ pp_closed_count }} завершённых
{% endif %}
+{{ pp_closed_count }} завершённых
{% endif %} {# планы без проекта этого бизнеса (идеи переехали на отдельный экран /ideas) #} {% if g.orphan_plans %}
📋 Планы без проекта
Планы без проекта ({{ g.orphan_plans|length }}) — лежат в репозитории этого бизнеса. Чтобы план встал под проект, добавьте его в links: карточки:
{% for pl in g.orphan_plans %} 📋{{ pl.title }} {{ pl.status_ru }} {% endfor %}
{% endif %} {% endfor %} {% if pp_groups_with_projects %} {% endif %}