mirror of
https://github.com/azaion/ui.git
synced 2026-06-21 17:51:10 +00:00
510df68bcf
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>
214 lines
7.1 KiB
Markdown
214 lines
7.1 KiB
Markdown
# Resource Limit Tests
|
|
|
|
The SPA's resource constraints are bundle size (initial JS), upload size cap (server), runtime image footprint (`nginx:alpine` only), and exclusion of the unbundled `mission-planner/` from production output. Long-session memory / CPU behavior is also covered here at a documentary level — no AC binds a hard runtime memory budget today.
|
|
|
|
### NFT-RES-LIM-01: Initial JS bundle ≤ 2 MB gzipped
|
|
|
|
**Traces to**: AC-11, O13
|
|
|
|
**Preconditions**:
|
|
- `bun run build` has produced `dist/`.
|
|
|
|
**Monitoring**:
|
|
- Sum of gzipped initial-route JS chunk sizes (computed from Vite's `manifest.json`).
|
|
|
|
**Duration**: ≤ 60 s (build + measurement).
|
|
**Pass criteria**: total gzipped initial JS ≤ 2 097 152 bytes (`results_report.md` row 40). Documentary today; CI gate target.
|
|
**Expected result source**: `results_report.md` row 40.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-02: nginx `client_max_body_size 500M`
|
|
|
|
**Traces to**: AC-10, E9
|
|
|
|
**Preconditions**:
|
|
- `nginx.conf` present in the repo (and in the built image's `/etc/nginx/`).
|
|
|
|
**Monitoring**:
|
|
- Read the value of `client_max_body_size` from `nginx.conf`.
|
|
|
|
**Duration**: ≤ 5 s.
|
|
**Pass criteria**: value equals `500M` (`results_report.md` row 38).
|
|
**Expected result source**: `results_report.md` row 38.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-03: Production image is `nginx:alpine` and carries no Node.js
|
|
|
|
**Traces to**: AC-33, S5, O11
|
|
|
|
**Preconditions**:
|
|
- Built image `azaion/ui:<tag>` available locally.
|
|
|
|
**Monitoring**:
|
|
- `docker inspect azaion/ui:<tag>` for the final stage's base image.
|
|
- Filesystem scan inside the image for a `node` binary.
|
|
|
|
**Duration**: ≤ 30 s.
|
|
**Pass criteria**: base image is `nginx:alpine`; no `node` binary present (`results_report.md` row 42).
|
|
**Expected result source**: `results_report.md` row 42.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-04: `mission-planner/` is excluded from production bundle
|
|
|
|
**Traces to**: AC-31, O12, ADR-009
|
|
|
|
**Preconditions**:
|
|
- `bun run build` has produced `dist/`.
|
|
|
|
**Monitoring**:
|
|
- Vite's build report / manifest for chunk origins.
|
|
- Static-import graph analysis starting from `src/main.tsx` — verify no edges into `mission-planner/`.
|
|
|
|
**Duration**: ≤ 30 s.
|
|
**Pass criteria**: no `dist/**` file originates from `mission-planner/**`; the import graph from `src/main.tsx` does NOT reach `mission-planner/` (`results_report.md` row 41).
|
|
**Expected result source**: `results_report.md` row 41.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-05: SPA memory stable across a 30-minute annotation session
|
|
|
|
**Traces to**: H2 (edge deploy), AC-09 (SSE)
|
|
**Status**: documentary — no AC binds a hard runtime memory budget today
|
|
|
|
**Preconditions**:
|
|
- E2E profile; user logged in on `/annotations`; annotation-status SSE open.
|
|
|
|
**Monitoring**:
|
|
- Headless Chromium `performance.memory.usedJSHeapSize` sampled every 60 s for 30 min.
|
|
|
|
**Duration**: 30 min.
|
|
**Pass criteria**: `usedJSHeapSize` does not grow by more than 50 % over the session under steady-state interaction (open/close media, page through dataset). A documentary baseline; if Phase 3 deems it un-anchored to an AC, it is downgraded to a metric-only run.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-06: Live-GPS SSE 1-hour soak — no listener leak, no memory creep
|
|
|
|
**Traces to**: AC-08
|
|
**Status**: documentary
|
|
|
|
**Preconditions**:
|
|
- E2E profile; flight selected; live-GPS simulator emits at 1 Hz.
|
|
|
|
**Monitoring**:
|
|
- `EventSource` instance count sampled every 60 s — must stay at exactly 1.
|
|
- `usedJSHeapSize` sampled every 60 s.
|
|
|
|
**Duration**: 60 min.
|
|
**Pass criteria**: EventSource count stays at 1 throughout; heap grows by ≤ 30 % (documentary).
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-07: 100 sequential flight selections — no leaked SSEs, no leaked Contexts
|
|
|
|
**Traces to**: AC-08, P4
|
|
**Status**: documentary
|
|
|
|
**Preconditions**:
|
|
- E2E profile; ≥ 5 flights in seed.
|
|
|
|
**Monitoring**:
|
|
- Total EventSource instances created over the loop.
|
|
- Final open EventSource count (after deselect-then-reselect cycles end at "deselected").
|
|
|
|
**Duration**: ≤ 5 min.
|
|
**Pass criteria**: after the loop, open EventSource count is ≤ 1 (only the currently-selected stream if any). No more than `100 + 1 ` EventSources were created in total (one extra for any pre-test state). Documentary; Phase 3 to confirm or downgrade.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-08: Edge-host RAM profile of the UI image at steady state
|
|
|
|
**Traces to**: H2
|
|
**Status**: documentary; hardware-assessment phase will pin the exact numbers
|
|
|
|
**Preconditions**:
|
|
- Production image running on the target edge profile (2 vCPU, 4 GB RAM).
|
|
|
|
**Monitoring**:
|
|
- `docker stats azaion-ui` sampled every 10 s for 5 min while a user is actively on `/annotations` with one open SSE.
|
|
|
|
**Duration**: 5 min.
|
|
**Pass criteria**: RSS of the nginx process under sustained traffic stays under 200 MB (documentary baseline; will be tightened or relaxed at hardware-assessment time).
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-09: nginx routes — exactly 9 location blocks for the suite services
|
|
|
|
**Traces to**: AC-34, E2
|
|
|
|
**Preconditions**:
|
|
- `nginx.conf` present.
|
|
|
|
**Monitoring**:
|
|
- Parse `nginx.conf` for `location` blocks under the main `server`.
|
|
|
|
**Duration**: ≤ 5 s.
|
|
**Pass criteria**: `location` block set equals `{/api/admin/, /api/flights/, /api/annotations/, /api/detect/, /api/loader/, /api/gps-denied-desktop/, /api/gps-denied-onboard/, /api/autopilot/, /api/resource/}` (`results_report.md` row 43).
|
|
**Expected result source**: `results_report.md` row 43.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-10: nginx — each route strips its `/api/<service>/` prefix
|
|
|
|
**Traces to**: AC-34, E2
|
|
|
|
**Preconditions**:
|
|
- `nginx.conf` present.
|
|
|
|
**Monitoring**:
|
|
- Per `location` block, inspect the `proxy_pass` / `rewrite` directive shape — verify the prefix is stripped before forwarding upstream.
|
|
|
|
**Duration**: ≤ 5 s.
|
|
**Pass criteria**: every block satisfies the strip-prefix regex (per-block check, `results_report.md` row 44).
|
|
**Expected result source**: `results_report.md` row 44.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-11: CI image tag scheme is `${branch}-arm`
|
|
|
|
**Traces to**: AC-32, E7
|
|
|
|
**Preconditions**:
|
|
- `.woodpecker/build-arm.yml` present.
|
|
|
|
**Monitoring**:
|
|
- Parse the push step's `tag` field for branches `dev`, `stage`, `main`.
|
|
|
|
**Duration**: ≤ 5 s.
|
|
**Pass criteria**: pushed tag for branch `main` matches `^main-arm$` (`results_report.md` row 70). Same regex shape for `dev` and `stage` (derived).
|
|
**Expected result source**: `results_report.md` row 70.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-12: OCI labels present on the pushed image
|
|
|
|
**Traces to**: AC-32, E6
|
|
|
|
**Preconditions**:
|
|
- `.woodpecker/build-arm.yml` present.
|
|
|
|
**Monitoring**:
|
|
- Parse the push step's label declarations — count and presence.
|
|
|
|
**Duration**: ≤ 5 s.
|
|
**Pass criteria**: labels `org.opencontainers.image.revision`, `org.opencontainers.image.created`, `org.opencontainers.image.source` are all declared and non-empty; total label count == 3 (`results_report.md` row 71).
|
|
**Expected result source**: `results_report.md` row 71.
|
|
|
|
---
|
|
|
|
### NFT-RES-LIM-13: Revision label equals `$CI_COMMIT_SHA`
|
|
|
|
**Traces to**: AC-32, E5
|
|
|
|
**Preconditions**:
|
|
- `.woodpecker/build-arm.yml` present.
|
|
|
|
**Monitoring**:
|
|
- Parse the label value template for `org.opencontainers.image.revision`.
|
|
|
|
**Duration**: ≤ 5 s.
|
|
**Pass criteria**: label value template equals `$CI_COMMIT_SHA` (or the pipeline's documented equivalent) (`results_report.md` row 72).
|
|
**Expected result source**: `results_report.md` row 72.
|