project.html

  1{% extends "base.html" %}
  2
  3{% block title %}td — {{ project_name }}{% endblock %}
  4
  5{% block content %}
  6<nav aria-label="Breadcrumb">
  7  <ol class="unstyled hstack">
  8    <li><a href="/" class="unstyled">Projects</a></li>
  9    <li aria-hidden="true">/</li>
 10    <li><a href="/projects/{{ project_name }}" class="unstyled" aria-current="page"><strong>{{ project_name }}</strong></a></li>
 11  </ol>
 12</nav>
 13
 14<h1>{{ project_name }}</h1>
 15
 16<div class="container">
 17  <div class="row">
 18    <article class="card col-4">
 19      <h2>Open</h2>
 20      <p><strong>{{ stats_open }}</strong></p>
 21    </article>
 22    <article class="card col-4">
 23      <h2>In progress</h2>
 24      <p><strong>{{ stats_in_progress }}</strong></p>
 25    </article>
 26    <article class="card col-4">
 27      <h2>Closed</h2>
 28      <p><strong>{{ stats_closed }}</strong></p>
 29    </article>
 30  </div>
 31</div>
 32
 33{% if !next_up.is_empty() %}
 34<details open class="mt-4">
 35  <summary><h2>Next up</h2></summary>
 36  <div class="table">
 37    <table>
 38      <caption class="sr-only">Top scored tasks recommended to work on next</caption>
 39      <thead>
 40        <tr>
 41          <th scope="col">#</th>
 42          <th scope="col">ID</th>
 43          <th scope="col">Score</th>
 44          <th scope="col">Title</th>
 45        </tr>
 46      </thead>
 47      <tbody>
 48        {% for (i, s) in next_up.iter().enumerate() %}
 49        <tr>
 50          <td>{{ i + 1 }}</td>
 51          <td><a href="/projects/{{ project_name }}/tasks/{{ s.id }}"><code>{{ s.short_id }}</code></a></td>
 52          <td>{{ s.score }}</td>
 53          <td>{{ s.title }}</td>
 54        </tr>
 55        {% endfor %}
 56      </tbody>
 57    </table>
 58  </div>
 59</details>
 60{% endif %}
 61
 62<details open class="mt-4">
 63  <summary><h2>Tasks</h2></summary>
 64
 65  <form method="get" action="/projects/{{ project_name }}" class="hstack gap-2 mt-2 mb-4">
 66    <div data-field>
 67      <label for="filter-status">Status</label>
 68      <select id="filter-status" name="status" aria-label="Filter by status">
 69        <option value="">All</option>
 70        <option value="open"{% if filter_status.as_deref() == Some("open") %} selected{% endif %}>Open</option>
 71        <option value="in_progress"{% if filter_status.as_deref() == Some("in_progress") %} selected{% endif %}>In progress</option>
 72        <option value="closed"{% if filter_status.as_deref() == Some("closed") %} selected{% endif %}>Closed</option>
 73      </select>
 74    </div>
 75    <div data-field>
 76      <label for="filter-priority">Priority</label>
 77      <select id="filter-priority" name="priority" aria-label="Filter by priority">
 78        <option value="">All</option>
 79        <option value="high"{% if filter_priority.as_deref() == Some("high") %} selected{% endif %}>High</option>
 80        <option value="medium"{% if filter_priority.as_deref() == Some("medium") %} selected{% endif %}>Medium</option>
 81        <option value="low"{% if filter_priority.as_deref() == Some("low") %} selected{% endif %}>Low</option>
 82      </select>
 83    </div>
 84    <div data-field>
 85      <label for="filter-effort">Effort</label>
 86      <select id="filter-effort" name="effort" aria-label="Filter by effort">
 87        <option value="">All</option>
 88        <option value="low"{% if filter_effort.as_deref() == Some("low") %} selected{% endif %}>Low</option>
 89        <option value="medium"{% if filter_effort.as_deref() == Some("medium") %} selected{% endif %}>Medium</option>
 90        <option value="high"{% if filter_effort.as_deref() == Some("high") %} selected{% endif %}>High</option>
 91      </select>
 92    </div>
 93    <div data-field>
 94      <label for="filter-label">Label</label>
 95      <select id="filter-label" name="label" aria-label="Filter by label">
 96        <option value="">All</option>
 97        {% for l in all_labels %}
 98        <option value="{{ l }}"{% if filter_label.as_deref() == Some(l.as_str()) %} selected{% endif %}>{{ l }}</option>
 99        {% endfor %}
100      </select>
101    </div>
102    <div data-field>
103      <label for="filter-search">Search</label>
104      <input type="text" id="filter-search" name="q" value="{{ filter_search }}" placeholder="Search titles…" aria-label="Search tasks by title">
105    </div>
106    <button type="submit" class="outline">Filter</button>
107  </form>
108
109  {% if page_tasks.is_empty() %}
110  <p class="text-light">No tasks match the current filters.</p>
111  {% else %}
112  <div class="table">
113    <table>
114      <caption class="sr-only">Task list for project {{ project_name }}</caption>
115      <thead>
116        <tr>
117          <th scope="col">ID</th>
118          <th scope="col">Status</th>
119          <th scope="col">Priority</th>
120          <th scope="col">Effort</th>
121          <th scope="col">Title</th>
122        </tr>
123      </thead>
124      <tbody>
125        {% for t in page_tasks %}
126        <tr>
127          <td><a href="/projects/{{ project_name }}/tasks/{{ t.full_id }}"><code>{{ t.short_id }}</code></a></td>
128          <td><span class="badge{% if t.status == "closed" %} success{% elif t.status == "in_progress" %} secondary{% endif %}">{{ t.status }}</span></td>
129          <td>{{ t.priority }}</td>
130          <td>{{ t.effort }}</td>
131          <td>{{ t.title }}</td>
132        </tr>
133        {% endfor %}
134      </tbody>
135    </table>
136  </div>
137
138  {% if total_pages > 1 %}
139  <nav aria-label="Task list pagination" class="mt-4">
140    <menu class="buttons">
141      {% if page > 1 %}
142      {% let prev = page - 1 %}
143      <li><a href="{{ self.pagination_href(prev) }}" class="button outline small">← Previous</a></li>
144      {% endif %}
145      {% for p in pagination_pages %}
146      <li>
147        {% if *p == page %}
148        <a href="{{ self.pagination_href(p) }}" class="button small" aria-current="page">{{ p }}</a>
149        {% else %}
150        <a href="{{ self.pagination_href(p) }}" class="button outline small">{{ p }}</a>
151        {% endif %}
152      </li>
153      {% endfor %}
154      {% if page < total_pages %}
155      {% let next = page + 1 %}
156      <li><a href="{{ self.pagination_href(next) }}" class="button outline small">Next →</a></li>
157      {% endif %}
158    </menu>
159  </nav>
160  {% endif %}
161  {% endif %}
162</details>
163{% endblock %}