Files
ui/_docs/02_document/FINAL_report.md
Oleksandr Bezdieniezhnykh 510df68bcf [AZ-447] autodev Steps 1-4 baseline: docs, tests, refactor specs
Captures the full output of autodev existing-code Phase A through
Step 4 (Code Testability Revision) for the Azaion UI workspace:

- Step 1 Document: _docs/02_document/ (FINAL_report, architecture,
  glossary, components/, modules/, diagrams/, system-flows,
  module-layout) plus _docs/00_problem/ + _docs/01_solution/ +
  _docs/legacy/ + _docs/how_to_test + README.
- Step 2 Architecture Baseline: architecture_compliance_baseline.md.
- Step 3 Test Spec: _docs/02_document/tests/ (environment,
  test-data, blackbox/performance/resilience/security/
  resource-limit tests, traceability-matrix), enum_spec_snapshot,
  expected_results/results_report.md (98 rows), plus the
  run-tests.sh + run-performance-tests.sh runners.
- Step 4 Code Testability Revision: 01-testability-refactoring/
  run dir (list-of-changes C01-C07, deferred_to_refactor,
  analysis/research_findings + refactoring_roadmap) and the 7
  child task specs AZ-448..AZ-454 under _docs/02_tasks/todo/
  plus _dependencies_table.md.
- _docs/_autodev_state.md pins the cursor at Step 4 / refactor
  Phase 4 entry so /autodev resumes cleanly.

Epic AZ-447 (UI testability gates) tracks the 7 child tasks that
will land in subsequent commits.

Co-authored-by: Cursor <cursoragent@cursor.com>
2026-05-11 00:38:49 +03:00

23 KiB
Raw Permalink Blame History

Azaion UI — Final Documentation Report

Output of /document Step 7. Integrates all artifacts produced in Steps 06. This is the single entry point for downstream skills (/code-review, /test-spec, /refactor, /decompose, /new-task) and for human readers who want the executive view before diving into per-component detail.

Status: complete Date: 2026-05-10 Scope: full codebase (src/ + mission-planner/ port-source)


1. Executive summary

Azaion UI is the operator-facing browser SPA of the Azaion UAV operations suite — a static-bundle React 19 application served by nginx:alpine inside an ARM64 container. It is the in-progress React rewrite of the legacy WPF stack (Azaion.Annotator + Azaion.Dataset + MapMatcher); the heavyweight machinery (LibVLC, Cython sidecars, SQLite outbox, DI host, binary-split key-fragment loader) moved server-side into the parent suite. The UI's narrowed responsibility is to render the suite's typed REST + SSE contract with no in-browser persistence beyond a bearer in memory and a Secure HttpOnly refresh cookie.

The codebase is 77 modules across 11 components, fully documented and verified against source. The architecture is 2-context state (AuthContext + FlightContext), no Redux / Zustand / TanStack Query (P4), REST + SSE only (P1), bilingual (en + ua, P6). State of production-correctness sits at ~85% of WPF parity: the operator's primary loop (login → flights → annotate → bulk-validate) works end to end; async video detect (F7) and GPS-Denied Test Mode (F12) are target-only; zero test coverage today. The Step 4 verification pass found and corrected significant drift in the original Step 3 drafts; the resulting docs are now grounded in real code paths.

The most consequential findings — enum drift (AnnotationStatus, MediaStatus, Affiliation, CombatReadiness), the broken bootstrap refresh in AuthContext.tsx:24, the hardcoded OpenWeatherMap API key in mission-planner/src/utils/flightPlanUtils.ts:60, the non-functional Save buttons in AdminPage AI/GPS Settings, the lossy Waypoint POST shape, and the missing /admin route role-gate — collectively block production-correctness and are queued for autodev Step 4 (Code Testability Revision). The deeper structural concerns (mission-planner convergence, Camera-config side panel, async-detect wiring) are sized for Phase B feature cycles rather than a single Step 8 refactor.


2. Problem statement

The Azaion suite operates UAV / aerial-imagery missions for military and defense use cases. Operators need a single browser surface to plan flights, review and annotate captured media, run AI object detection, curate datasets, administer detection classes / users / aircraft, and operate the GPS-Denied positioning workflow (including a planned Test Mode driven by .tlog + video pairs through SITL).

This SPA is that surface. It serves:

  • Operator — primary persona, default /flights route, bilingual UI.
  • Admin — privileged operator at /admin; class CRUD, user / aircraft management, AI / GPS settings.
  • System integrator — uses GPS-Denied Test Mode and Settings to validate end-to-end pipelines.

It is internal, not public. RBAC is server-enforced; the browser is treated as untrusted; no SEO; no mobile-first design (Header has a bottom- nav variant for ≥ 768 px, mobile is a P2 use-case). Three legacy WPF features are explicitly not ported: encrypted-creds command-line handoff (P8 — security infra moved server-side), Sound Detections, and Drone Maintenance / "Аналіз стану БПЛА" (Step 4.5 decisions — dropped).

Full statement: _docs/00_problem/problem.md.


3. Architecture overview

Tech stack (one-liner): React 19 + TypeScript 5.7 strict + Vite 6 + Bun 1.3.11 + Tailwind 4 (az-* design tokens) + react-router-dom@7 + leaflet@1.9.4 + react-leaflet@5 + chart.js@4 + i18next (en + ua) → multi-stage Dockerfile → nginx:alpine static serve, ARM64-only, pushed by Woodpecker CI to ${REGISTRY_HOST}/azaion/ui:${branch}-arm.

Layering (module-layout.md):

  • L0 — Foundation: 00_foundation, 11_class-colors
  • L1 — Transport: 01_api-transport (fetch + EventSource wrappers)
  • L2 — Auth & Shared UI: 02_auth, 03_shared-ui
  • L3 — Feature pages: 04_login, 05_flights, 06_annotations, 07_dataset, 08_admin, 09_settings
  • L4 — App shell: 10_app-shell

Cross-cutting principles (binding constraints — architecture.md § Architecture Vision):

P1 REST + SSE only · P2 Static bundle + nginx · P3 Bearer in memory + HttpOnly refresh cookie · P4 Two-context state · P5 ARM-first edge · P6 Bilingual (en + ua) · P7 Lift cross-cutting at 2+ touches · P8 WPF parity is a goal not a constraint · P9 Spec is source of truth for numeric enums · P10 No hardcoded credentials · P11 Persist what you type · P12 Admin can edit existing detection classes.

Full architecture: _docs/02_document/architecture.md.


4. Component summary

# Component Purpose Direct deps (components) Files / size
00 00_foundation Types, hooks (useDebounce, useResizablePanel), i18n bundles src/types/index.ts, src/hooks/*, src/i18n/*, src/components/DetectionClasses.tsx
01 01_api-transport fetch wrapper (client.ts) + EventSource wrapper (sse.ts); 401-retry refresh 00 src/api/client.ts, src/api/sse.ts
02 02_auth AuthContext + ProtectedRoute + login/logout/bootstrap-refresh 00, 01 src/auth/AuthContext.tsx, src/auth/ProtectedRoute.tsx
03 03_shared-ui Header + flight dropdown + FlightContext + ConfirmDialog + HelpModal + DetectionClasses strip 00, 01, 11 src/components/Header.tsx, FlightContext.tsx, ConfirmDialog.tsx, HelpModal.tsx, DetectionClasses.tsx
04 04_login Public /login route 00, 02 src/features/login/LoginPage.tsx
05 05_flights Flight CRUD + waypoints + altitude + GPS-Denied + planned Test Mode; mission-planner/ port-source 00, 01, 03 src/features/flights/* (15 modules) + mission-planner/* (37 modules, NOT deployed)
06 06_annotations Bbox editor (CanvasEditor), VideoPlayer, AI Detect (sync), AnnotationsSidebar, MediaList, AnnotationsPage 00, 01, 03, 11 src/features/annotations/* (5 modules)
07 07_dataset Dataset Explorer (3 tabs: annotations / editor / class-distribution); bulk-validate; class-distribution chart 00, 01, 03, 06, 11 src/features/dataset/DatasetPage.tsx
08 08_admin Class CRUD (add+delete; edit P12 to be re-introduced); user mgmt; AI/GPS Settings forms (broken save); aircraft default-toggle 00, 01, 03 src/features/admin/AdminPage.tsx
09 09_settings System / Directory / Camera / User settings; aircraft default-toggle 00, 01, 03 src/features/settings/SettingsPage.tsx
10 10_app-shell App.tsx + main.tsx + routing tree + global CSS 00, 02, 03, 04, 05, 06, 07, 08, 09 src/App.tsx, src/main.tsx, src/index.css, index.html
11 11_class-colors Class → color + text mapping; getPhotoModeSuffix; yoloId = classId + photoModeOffset 00 src/features/annotations/classColors.ts (file move pending)

Full per-component specs: _docs/02_document/components/*/description.md.


5. System flows

# Flow Trigger Status today
F1 Login /login form submit Works
F2 Bearer auto-refresh on 401 Authenticated fetch returns 401 Two paths: 401-retry POST works; bootstrap GET broken (Step 4 fix)
F3 Select active flight Flight dropdown in Header Works (corrected at Step 4 — persists via UserSettings, not /flights/select)
F4 Create / save flight + waypoints Save in FlightsPage Works but lossy: delete-then-recreate waypoint cycle; POST shape mismatches spec (Step 4 fix)
F5 Annotate media (manual bbox) Drag on canvas Works; save body missing Source, WaypointId; uses time not videoTime (Step 4 fix)
F6 AI Detect — image (sync) Click AI Detect with image Works
F7 AI Detect — video (async) Click AI Detect with video NOT WIRED today; sync F6 is used as a bridge for short videos. Phase B target.
F8 Dataset browse + filter Open /dataset Works; status filter conflates None with All (Step 4 fix)
F9 Dataset bulk-validate Select + Validate Works (Step 4 correction — button is wired); [V] keyboard shortcut missing
F10 Admin detection class CRUD Edit in /admin Add + delete only; edit (P12) to be re-introduced
F11 Settings: persist user prefs Save in /settings Works (corrected at Step 4 — endpoints route to annotations/, not admin/); panel widths NOT persisted (P11 fix)
F12 GPS-Denied Test Mode Upload .tlog + video NOT WIRED today; Phase B target.
F13 Live-GPS SSE FlightsPage with selected flight Works (newly added at Step 4)
F14 Annotation-status SSE AnnotationsPage with media Works (newly added at Step 4 — separate stream from F7 detect-progress)

Full sequence diagrams + error scenarios: _docs/02_document/system-flows.md.


6. Risk observations (from 04_verification_log.md)

High-priority — block production-correctness (Step 4 fix candidates)

# Risk Component Source
R1 Bootstrap refresh missing credentials:'include' — cold load fails to refresh, forces unnecessary re-login 02_auth/AuthContext AuthContext.tsx:24; F2
R2 Numeric enum drift (AnnotationStatus, MediaStatus, Affiliation, CombatReadiness) — wire payloads will be wrong 00_foundation src/types/index.ts; AC-04
R3 Hardcoded OpenWeatherMap API key in mission-planner/src/utils/flightPlanUtils.ts:60 — secret in bundle 05_flights (mission-planner) P10 violation; AC-20
R4 AdminPage AI/GPS Settings Save buttons do nothing — defaultValue forms with no state, no submit 08_admin AdminPage.tsx; finding B4
R5 Lossy Waypoint POST shape — UI sends {name, latitude, longitude, order}; spec wants {Geopoint:{Lat,Lon,MGRS}, Source, Objective, OrderNum, Height} — likely 400s on a strict server 05_flights finding #20
R6 Annotation save body missing Source, WaypointId; field renamed time → videoTime 06_annotations finding #32
R7 /admin route lacks client-side role-gate — non-admin sees broken admin UI flicker before server 403 10_app-shell + 08_admin AC-22
R8 Async video detect (F7) NOT WIRED — sync /api/detect/${id} is silently used for video; long videos blow access-token TTL (no X-Refresh-Token) 06_annotations F7; finding #29

Medium-priority — quality / a11y / hygiene

# Risk Component Source
R9 Annotation overlay window symmetric ±200 ms instead of asymmetric [-50, +150] ms (matches WPF) 06_annotations/CanvasEditor finding #6; AC-28
R10 useResizablePanel reads UserSettings.panelWidths but never writes back — P11 violation 00_foundation + 06_annotations/07_dataset AC-21
R11 MediaList uses alert() instead of toast / dialog 06_annotations AC-14
R12 ConfirmDialog lacks aria-modal / role=dialog / focus-trap / Esc 03_shared-ui AC-15
R13 Header flight dropdown lacks role=combobox / aria-expanded / Esc-to-close / focus-trap; outside-click handler always attached 03_shared-ui AC-16
R14 AdminPage.handleDeleteClass lacks ConfirmDialog despite being destructive 08_admin AC-30
R15 09_settings numeric inputs use parseInt(v) || 0 — empty silently writes 0 09_settings AC-26
R16 09_settings save handlers lack try/finally — PUT failure leaves saving:true permanently 09_settings AC-27
R17 i18next.lng hardcoded 'en' — no detector / no persistence 00_foundation AC-13
R18 Hardcoded English strings in AdminPage, HelpModal 08_admin + 03_shared-ui P6 violation
R19 mapIcons.ts defaultIcon CDN URL pinned to leaflet@1.7.1 while package uses 1.9.4 05_flights finding
R20 magic mediaType=1 literal in 06_annotations and 07_dataset 06_annotations + 07_dataset AC-29
R21 classNum=0 sentinel collides with real class 0 in dataset filters 07_dataset finding #9
R22 Dataset status filter conflates None with All 07_dataset finding
R23 DatasetPage editor tab does not save 07_dataset finding #4
R24 AnnotationsPage.handleDownload tainted-canvas risk 06_annotations finding
R25 AnnotationsPage.handleSave fallback hides save loss 06_annotations finding
R26 mission-planner/flightPlanUtils.ts silently swallows weather errors; sequential await per segment (perf trap); ambiguous battery-capacity unit (Wh vs Ws); km vs m altitude mixing 05_flights (port-source) findings

Low-priority — surface / polish

# Risk Component Source
R27 No ErrorBoundary at the app root 10_app-shell finding
R28 No lazy code-splitting / chunked routes — bundle bloat 10_app-shell finding (AltitudeChart lazy-load opportunity)
R29 index.html body class hardcodes hex literals instead of az-* tokens 10_app-shell discovery #11.10
R30 runUnlockSequence 4×600 ms theatrical animation in LoginPage 04_login finding B4
R31 FlightContext.selectFlight is fire-and-forget — no error path 03_shared-ui finding B3
R32 FlightContext.GET /api/flights?pageSize=1000 hardcoded ceiling 03_shared-ui finding B3

CI / infra-level (Step 6 surface — track at suite level)

# Risk Source
R33 No CSP / hardening headers in nginx.conf security_approach.md § 9
R34 No vulnerability scan / SBOM emission / image signing in CI architecture.md § 3 "Missing from the pipeline today"
R35 No test step in CI today .woodpecker/build-arm.yml
R36 No AMD64 build (ARM64-only image) .woodpecker/build-arm.yml
R37 No browser-list config (browser support matrix not enforced) architecture.md § 6
R38 No bundle-size budget gate architecture.md § 6; AC-11
R39 EventSource refresh-rotation breaks open SSE; no reconnect logic architecture.md § Architecture Vision; AC-24
R40 No centralized client telemetry (only browser-console logging) deployment/observability.md

7. Open questions

These were flagged during analysis and remain undecided. They do NOT block downstream skills; each is owned by a specific phase per architecture.md § Architecture Vision Open Questions.

# Question Owner / planned resolution
Q1 Test framework choice (Vitest / Jest / Playwright / Bun:test) Autodev Step 5 — Decompose Tests
Q2 IsSeed annotation visual (8 px IndianRed border) — does the modern API still expose isSeed? Phase B feature cycle
Q3 Camera-config side panel (GSD = altitude × focal × sensor) — per-user, per-flight, or per-detect-job? Phase B feature cycle
Q4 Status-bar clock + help-text-blink — port WPF UX or replace with toasts? Phase B feature cycle
Q5 OpenWeatherMap routing — .env (interim) or proxy via flights/ (preferred long-term)? Step 4 (interim); Phase B (proxy)
Q6 mission-planner/ end-state — delete after parity port (preferred per Step 4.5) or keep as continuously-vendored reference? Final Phase B cycle
Q7 Sync /api/detect/${id} for video — when in Phase B does the async pipeline (F7) ship? Phase B feature cycle
Q8 Module-layout Verification Needed (8 items) — class-colors file move, CanvasEditor cross-feature import, barrel exports, mission-planner/ ownership timing, foundation multi-dir, app-shell location, test layout, 11_class-colors location Step 4 / Phase B (per item)

8. Artifact index

All paths are workspace-relative. Each artifact's Status field declares who confirmed it (derived-from-code / synthesised-from-verified-docs / confirmed-by-user).

_docs/02_document/ — Documentation skill outputs

Artifact Step Purpose
00_discovery.md 0 Tech stack, dep graph, topological order, entry points, leaves
modules/*.md (22 files) 1 Per-module documentation — covers all 77 source modules
components/00_foundation/description.md 2 Foundation component spec
components/01_api-transport/description.md 2 API transport spec
components/02_auth/description.md 2 Auth spec
components/03_shared-ui/description.md 2 Shared UI spec
components/04_login/description.md 2 Login spec
components/05_flights/description.md 2 Flights spec (incl. mission-planner port-source)
components/06_annotations/description.md 2 Annotations spec (incl. WPF gap analysis §6b)
components/07_dataset/description.md 2 Dataset spec (incl. WPF gap analysis §6b)
components/08_admin/description.md 2 Admin spec
components/09_settings/description.md 2 Settings spec
components/10_app-shell/description.md 2 App-shell spec
components/11_class-colors/description.md 2 Class-colors spec (lifted at Step 2)
diagrams/components.md 2 Mermaid component dependency graph
module-layout.md 2.5 File-ownership map (consumed by /implement, /code-review, /refactor)
architecture.md 3a + 4.5 System architecture + § Architecture Vision (12 principles, mission-planner convergence plan)
system-flows.md 3b F1F14 sequence diagrams + error scenarios
data_model.md 3c Entity-relationship + numeric-enum drift map
deployment/containerization.md 3d Multi-stage Dockerfile, ARM64, nginx static serve
deployment/ci_cd_pipeline.md 3d Woodpecker pipeline structure
deployment/environment_strategy.md 3d Dev / Stage / Production
deployment/observability.md 3d Current state (no centralized telemetry)
04_verification_log.md 4 Coverage summary, corrections by document, pre-existing findings re-checked
glossary.md 4.5 Confirmed terminology + synonym/drift pairs
01_legacy_coverage_gaps.md (Step 2 → Step 4.5 update) WPF parity rollup; Sound Detections + Drone Maintenance marked "Intentionally not ported"
FINAL_report.md 7 This document
state.json (skill-internal) Document skill resumability state

_docs/01_solution/ — Solution synthesis

Artifact Step Purpose
solution.md 5 Retrospective solution: per-component table (Solution / Tools / Advantages / Limitations / Requirements / Security / Cost / Fit) for all 11 components; testing strategy; references

_docs/00_problem/ — Problem extraction

Artifact Step Purpose
problem.md 6a High-level problem statement + users + how-it-works + non-goals
restrictions.md 6b Hardware (4) / Software (14) / Environment (10) / Operational (15) restrictions
acceptance_criteria.md 6c 34 measurable ACs + 5 anti-criteria; coverage status
input_data/data_parameters.md 6d Typed REST entities + SSE payloads + env vars + static assets
security_approach.md 6e 13 sections covering auth, authz, tokens, SSE bearer, secrets, CORS, validation, XSS, nginx hardening, audit, supply-chain, fix-map

_docs/02_document/_autodev_state.md (parent: _docs/_autodev_state.md)

Artifact Purpose
_docs/_autodev_state.md Autodev resume pointer — flow / step / sub_step / cycle / retry_count

Reference inputs (existing, not produced by /document)

Artifact Purpose
_docs/legacy/wpf-era.md Legacy WPF reference — used as the WPF parity baseline
_docs/how_to_test.md GPS-Denied Test Mode reference
_docs/ui_design/* UI design wireframes — used in Step 4 cross-check
suite/_docs/* (parent suite) Service contracts — used for enum drift cross-check
suite/annotations-research (detached @ 22529c2) Read-only legacy WPF source — used in Step 2 / Step 4 cross-check

9. Coverage / completeness

Axis Result
Source modules 77 / 77 covered (22 doc files; some consolidated)
Components 11 / 11 specs
System flows 14 (F1F14; F7 + F12 are target-only by design)
Endpoint inventory Every api.*() and createSSE() call in src/ is reflected in architecture.md § 5
Test coverage 0 tests in src/ — no test framework configured today
BLOCKING gates passed Step 2 (components), Step 2.5 (module-layout), Step 4 (verification), Step 4.5 (glossary + vision), Step 6 (problem docs) — all confirmed by user

10. What comes next (autodev existing-code flow)

/document Step 1 of the autodev flow is now complete. The next steps are state-driven from _docs/_autodev_state.md:

  • Step 2 — Architecture Baseline Scan (code-review skill in baseline mode) → produces _docs/02_document/architecture_compliance_baseline.md marking pre-existing architecture violations (cycles, cross-component private imports, mission-planner convergence as a Critical Architecture finding).
  • Step 3 — Test Spec (test-spec skill) → produces _docs/02_document/tests/traceability-matrix.md and per-AC scenario files.
  • Step 4 — Code Testability Revision (refactor skill in guided mode) → addresses the High-priority risks above as a minimal, surgical testability prep.
  • Step 5 — Decompose Tests (decompose skill in tests-only mode) → selects test framework (Q1) and creates per-AC test tasks.
  • Steps 68 → Implement Tests / Run Tests / optional Refactor.
  • Phase B (Steps 917, looping) → Mission-planner convergence happens one feature group per cycle.

11. Ownership map (downstream-skill consumers)

Downstream skill Artifacts it reads first
/code-review (baseline mode) architecture.md § Architecture Vision, module-layout.md, 00_discovery.md § 8 (cross-layer imports)
/test-spec acceptance_criteria.md, system-flows.md, architecture.md § 6 NFRs
/refactor (guided mode for Step 4) 04_verification_log.md (high-priority risks), acceptance_criteria.md, module-layout.md
/decompose (tests-only mode) tests/traceability-matrix.md (produced by /test-spec), module-layout.md, restrictions.md
/implement per-task spec files in _docs/02_tasks/todo/, module-layout.md (file ownership)
/new-task (Phase B) architecture.md § Architecture Vision, glossary.md, 01_legacy_coverage_gaps.md

End of report.