What changed (ISS-055 — "can't load cargo if both planes are on same airport")
Root cause was UX: with ≥2 eligible planes at the origin, Load showed a plane dropdown + a disabled button until you picked one (single-plane path is one-click). The multi-plane branch had zero e2e coverage.
components/RightPane.tsx — LoadControls now preselects the first eligible plane: Load is one-click with N planes, and you can still pick another via the dropdown.
components/LeftPane.tsx — queue testids scoped by plane id (queue-leg-{plane.id}-{i}, queue-cancel-{plane.id}-{i}, queue-add-dest-{plane.id}, queue-add-{plane.id}) — with two on-board blocks the old unscoped ids were duplicates (Playwright strict-mode violations).
e2e/queue.spec.ts — locators updated to the scoped form.
New test hook POST /api/test/add-cash ({amount?}, default €1M, FLIGHT_TEST_HOOKS=1 gate like its siblings; outside the OpenAPI spec) — without it no e2e could afford a second plane (€200k vs starting €20k).
New e2e coverage: e2e/two-planes.spec.ts (serial, 6 tests)
Each test buys a second ATR through the real UI and resets the fleet to 1 plane before/after (heal + sell non-starters):
load — select shows both planes, preselected Load works one-click, per-plane loading via dropdown, both on-board blocks render with simultaneous cargo.
fly — both planes fly different legs; asserts ISS-057 semantics: slow-to-1× after landing (paused=false), resume to last selected speed when the last grounded plane dispatches (plus the negative case).
refuel — Refuel section lists both grounded planes; refueling one leaves the other's tank untouched, exact cost deducted.
relocate — relocate select lists both; relocating one leaves the starter untouched.
queue — per-plane queue add/cancel via scoped testids; auto-chain verified per plane at 1000×.
sell — sell list shows both; selling the second pays SELL_FRACTION×price and returns fleet to 1; selling the starter then 409s (last remaining).
Tests
tsc --noEmit clean · vitest 327 passed in 32 files (unchanged — no new unit tests; sibling test hooks have none) · playwright test --list: 52 tests in 14 files (was 46/13).
## What changed (ISS-055 — "can't load cargo if both planes are on same airport")
**Root cause was UX:** with ≥2 eligible planes at the origin, Load showed a plane dropdown + a **disabled** button until you picked one (single-plane path is one-click). The multi-plane branch had zero e2e coverage.
- `components/RightPane.tsx` — LoadControls now preselects the first eligible plane: Load is one-click with N planes, and you can still pick another via the dropdown.
- `components/LeftPane.tsx` — queue testids scoped by plane id (`queue-leg-{plane.id}-{i}`, `queue-cancel-{plane.id}-{i}`, `queue-add-dest-{plane.id}`, `queue-add-{plane.id}`) — with two on-board blocks the old unscoped ids were duplicates (Playwright strict-mode violations).
- `e2e/queue.spec.ts` — locators updated to the scoped form.
- New test hook `POST /api/test/add-cash` (`{amount?}`, default €1M, FLIGHT_TEST_HOOKS=1 gate like its siblings; outside the OpenAPI spec) — without it no e2e could afford a second plane (€200k vs starting €20k).
## New e2e coverage: `e2e/two-planes.spec.ts` (serial, 6 tests)
Each test buys a second ATR through the real UI and resets the fleet to 1 plane before/after (heal + sell non-starters):
1. **load** — select shows both planes, preselected Load works one-click, per-plane loading via dropdown, both on-board blocks render with simultaneous cargo.
2. **fly** — both planes fly different legs; asserts ISS-057 semantics: slow-to-1× after landing (paused=false), resume to last selected speed when the last grounded plane dispatches (plus the negative case).
3. **refuel** — Refuel section lists both grounded planes; refueling one leaves the other's tank untouched, exact cost deducted.
4. **relocate** — relocate select lists both; relocating one leaves the starter untouched.
5. **queue** — per-plane queue add/cancel via scoped testids; auto-chain verified per plane at 1000×.
6. **sell** — sell list shows both; selling the second pays SELL_FRACTION×price and returns fleet to 1; selling the starter then 409s (last remaining).
## Tests
- `tsc --noEmit` clean · vitest **327 passed in 32 files** (unchanged — no new unit tests; sibling test hooks have none) · `playwright test --list`: **52 tests in 14 files** (was 46/13).
- LoadControls preselects the first eligible plane so Load is one-click with N planes
- LeftPane queue testids scoped by plane id (queue-leg/cancel/add[-dest]-{plane.id})
— unscoped ids duplicated in the DOM with two on-board blocks
- new POST /api/test/add-cash hook (FLIGHT_TEST_HOOKS=1, default €1M) so e2e can
afford a second plane; returns the full state snapshot
- new serial spec e2e/two-planes.spec.ts: load, parallel fly + ISS-057 slow/resume,
refuel, relocate, per-plane queues with auto-chain, sell (6 tests)
- e2e/queue.spec.ts locators updated to the scoped testids
kamilkrzywda
scheduled this pull request to auto merge when all checks succeed 2026-09-20 23:33:26 +02:00
Blocking a user prevents them from interacting with repositories, such as opening or commenting on pull requests or issues. Learn more about blocking a user.
What changed (ISS-055 — "can't load cargo if both planes are on same airport")
Root cause was UX: with ≥2 eligible planes at the origin, Load showed a plane dropdown + a disabled button until you picked one (single-plane path is one-click). The multi-plane branch had zero e2e coverage.
components/RightPane.tsx— LoadControls now preselects the first eligible plane: Load is one-click with N planes, and you can still pick another via the dropdown.components/LeftPane.tsx— queue testids scoped by plane id (queue-leg-{plane.id}-{i},queue-cancel-{plane.id}-{i},queue-add-dest-{plane.id},queue-add-{plane.id}) — with two on-board blocks the old unscoped ids were duplicates (Playwright strict-mode violations).e2e/queue.spec.ts— locators updated to the scoped form.POST /api/test/add-cash({amount?}, default €1M, FLIGHT_TEST_HOOKS=1 gate like its siblings; outside the OpenAPI spec) — without it no e2e could afford a second plane (€200k vs starting €20k).New e2e coverage:
e2e/two-planes.spec.ts(serial, 6 tests)Each test buys a second ATR through the real UI and resets the fleet to 1 plane before/after (heal + sell non-starters):
Tests
tsc --noEmitclean · vitest 327 passed in 32 files (unchanged — no new unit tests; sibling test hooks have none) ·playwright test --list: 52 tests in 14 files (was 46/13).- LoadControls preselects the first eligible plane so Load is one-click with N planes - LeftPane queue testids scoped by plane id (queue-leg/cancel/add[-dest]-{plane.id}) — unscoped ids duplicated in the DOM with two on-board blocks - new POST /api/test/add-cash hook (FLIGHT_TEST_HOOKS=1, default €1M) so e2e can afford a second plane; returns the full state snapshot - new serial spec e2e/two-planes.spec.ts: load, parallel fly + ISS-057 slow/resume, refuel, relocate, per-plane queues with auto-chain, sell (6 tests) - e2e/queue.spec.ts locators updated to the scoped testids