feat: Sprint A Wahab review batch — categories, property hierarchy, priority grouping

Items 1-5, 9, 11 from denya-wahab-feedback-s2:
- Category.show_in_form (alert-only flag): Gas Leak hidden from issue picker
  but kept urgent for SLA/alert and reporting; emergency quick path on the
  new-issue form creates urgent tickets via include_hidden categories.
- Seed: Aluminum/Glass, Carpentry, Mould & Damp (Medium default) maintenance
  categories; Lost Property renamed Missing Item (+ sub).
- One alembic migration: add show_in_form (backfill True, Gas Leak False) +
  data rename Lost Property -> Missing Item.
- Property -> Building -> Apartment cascade with searchable apartment combobox
  on the new-issue form and ticket list filters; /api/tickets/units gains
  building filter + /units/grouped variant; /api/tickets gains additive
  building/unit_id filters. apartment_mapping.json committed (deterministic).
- Group-by-priority toggle on /tickets (four sections + unknown bucket,
  age-sortable, composes with filters, URL deep links), FM dashboard active
  tickets, and CS dashboard priority card click-through.
- Tests: 13 new (category visibility, seed idempotency/sync, unit grouping,
  ticket building/unit filters).
This commit is contained in:
root
2026-08-02 09:30:29 +00:00
parent 2e995ee758
commit 2407f294f4
16 changed files with 1579 additions and 97 deletions
+15
View File
@@ -116,6 +116,21 @@ Stored under `uploads/` with UUID filenames. Static-files mounted at `/uploads/`
SQLite via aiosqlite with async SQLAlchemy 2.0. Alembic for migrations.
Tables: users, units, categories, tickets, ticket_timeline, ticket_photos, escalations, whatsapp_log
## Categories & location (Sprint A)
- `Category.show_in_form` (default True) marks alert-only categories: `Gas Leak` is hidden
from the issue picker but keeps `sla_urgency="urgent"` for SLA/alert/reporting. Pickers
(`/api/tickets/categories[/flat]`) exclude them unless `include_hidden=true` (used by the
emergency quick path on `tickets/new.html`). Seed taxonomy lives in `app/services/seed.py`
(`SEED_CATEGORIES_DATA`); the Lost Property → Missing Item rename is a data migration
(alembic `b2f4a6c8e0d2`). Seeds are idempotent and sync `show_in_form` on existing rows.
- Location hierarchy is Property → Building → Apartment (uses `Unit.building`).
`GET /api/tickets/units/grouped` returns `{property: {building: [units]}}`;
`/api/tickets` accepts additive `building`/`unit_id` filters. Unit data is deterministic
from the committed `apartment_mapping.json` (built-in fallback in `seed.py`).
- Priority grouping ("Group by priority") is client-side via `app().groupByPriority()` in
`app/templates/base.html`; used by `tickets/list.html` and `dashboard/fm.html`.
## Maintaining this file
Keep this file for knowledge useful to almost every future agent session in this project.