Document ID: FF-BACKLOG-001
Sprint cadence: 2-week iterations
Last groomed: 2026-07-11
Board: FleetFlow Production Kanban
| Label | Meaning |
|---|---|
P0 |
Release blocker — security, ledger integrity, or dispatch failure |
P1 |
Core feature required for current phase exit criteria |
P2 |
Important enhancement, not phase-gating |
P3 |
Nice-to-have, backlog parking lot |
Goal: Enforce enterprise RBAC across API, web portal, and Flutter client with warehouse-scoped visibility and regional reporting for operations leadership.
Business value: Enables Bengkulu pilot → regional expansion without cross-tenant data leakage. Supports Merchant Admin self-service while giving Regional Managers and Fleet Operators governed oversight.
-
P0DefineUserRoleenum:SUPERADMIN,REGIONAL_MANAGER,HEAD_OF_WAREHOUSE,FLEET_OPERATOR,MERCHANT_ADMIN,DRIVER_PARTNER -
P0Implement permission matrix in@fleetflow/shared(PERMISSIONS,ROLE_PERMISSIONS) -
P0AddUserPrisma model withmerchantId/driverIdscoping links -
P0JWT login endpointPOST /v1/auth/loginwith role + password validation -
P0HybridAuthGuard: supportx-api-keyOR Bearer JWT on order endpoints -
P0PermissionsGuard+RequirePermissions/RequireAnyPermissiondecorators -
P0Seed six RBAC users with passwordFleetFlow!2026 -
P1Integration tests for order access scoping (rbac.integration.spec.ts)
-
P1AddWarehousemodel:id,regionCode,name,capacityLimit,currentLoad,hubLat,hubLng -
P1LinkDriver→warehouseIdfor hub assignment -
P1HEAD_OF_WAREHOUSEendpoints:GET /v1/warehouses/:id/utilization,PATCH /v1/warehouses/:id/capacity -
P1Enforce warehouse concurrent order cap before BullMQ enqueue -
P1CRUD UI in Next.js/admin/warehouseswith role guard -
P2Warehouse limit breach response:429 Too Many RequestswithRetry-Afterheader -
P2Audit log table:AuditEventwithactorId,action,entityType,entityId,metadata
-
P1GET /v1/reports/regional/orders— aggregated counts bystatus,vehicleTypeRequired, date range -
P1GET /v1/reports/regional/cancellations—MATCHINGfailure rate by hub -
P1GET /v1/reports/regional/ledger— read-only merchant wallet summary (no PII export) -
P2CSV export for Regional Manager dashboard -
P2Scheduled report email digest (weekly SLA summary)
-
P1GET /v1/fleet/drivers— paginated list withstatus,currentLat,currentLng,vehicle.type -
P1PATCH /v1/fleet/drivers/:id/status— transitionAVAILABLE|ON_TRIP|OFFLINE -
P1Real-time map component in Next.js showing driver pins (Mapbox / Google Maps) -
P2WebSocket or SSE channelfleet:positionsfor sub-5s telemetry refresh -
P2Geofence alert when driver exits assigned hub boundary -
P3Historical route playback for completed deliveries
Goal: Reliable automated driver matching using Haversine distance, BullMQ orchestration, and strict order state transitions from intake through assignment or cancellation.
Business value: Core product differentiator — sub-3-second matching SLA with transparent timeline audit for merchants and operators.
-
P0Haversine distance function with Earth radius 6371 km -
P0findClosestDriverWithinRadius— 10 km strict filter, ascending sort -
P0MatchingProcessorondispatch-queuewith@nestjs/bullmq -
P0State transitions:DRAFT→PENDING→MATCHING→ASSIGNED|CANCELLED -
P0OrderTimelineentries at every transition with human-readable notes -
P0Vehicle type hard filter:vehicle.type === order.vehicleTypeRequired -
P1Unit tests for geo-matching and pricing (geo-matching.service.spec.ts,pricing.service.spec.ts)
-
P0Idempotent job processing: guard against double-assignment if job retried -
P1Dead-letter queue for jobs exhausted after 3 attempts -
P1GET /v1/ops/queues/dispatch— queue depth, active jobs, failed count -
P1Metrics: job duration histogram, matching success rate counter -
P2Priority lanes: EXPRESS orders jump queue head -
P2Staggered retry per vehicle type when first pass finds zero candidates
-
P1Exponential backoff:attempts: 3,delay: 2000ms(baseline) -
P1Distinguish transient failures (DB connection) vs permanent (invalid order ID) -
P1Alert Fleet Operator when job lands in failed state after max retries -
P2Manual requeue endpoint:POST /v1/orders/:id/requeue(FLEET_OPERATORonly) -
P2Circuit breaker: pause enqueue if Redis unavailable > 30s
-
P1POST /v1/orders/:id/pickup— driver marksPICKED_UP -
P1POST /v1/orders/:id/deliver— driver marksDELIVERED, driver returnsAVAILABLE -
P1Flutter: wire active trip actions to live API -
P2Proof-of-delivery / departure photo upload (Cloudinary + local fallback) -
P2Ops manual completion override with audit reason -
P2Customer notification webhook onDELIVERED
-
P1Composite index(status, vehicleTypeRequired)ondriversjoinvehicles -
P1PostGIS extension evaluation for production geo queries -
P2Pre-computed hub bounding boxes to reduce candidate set before Haversine -
P3Python matching microservice extraction behind HTTP adapter
Goal: Double-entry style transaction bookkeeping with merchant prepaid wallets, driver partner payouts, and platform fee retention — all inside atomic Prisma transactions.
Business value: Financial trust for B2B merchants; auditable revenue capture for FleetFlow operations.
-
P0Transactionmodel:DEBIT|CREDIT, optionalmerchantId/driverId -
P0Merchant balance field onMerchantmodel -
P0Pre-create balance validation inOrdersService.createOrder -
P0Assignment-time debit + driver credit (90%) in matching processor transaction block -
P0Seed ledger entries for three merchants (low balance + sufficient balance scenarios) -
P1API key merchantff_live_merchant_startup_1b4d8e6f— insufficient balance test case
-
P0Re-read merchant balance inside assignment transaction (optimistic concurrency /SELECT FOR UPDATE) -
P1platformFeecolumn onOrder— explicitprice * 0.10persistence -
P1Transactionlinkage:orderIdforeign key on every order-related ledger row -
P1Ledger reconciliation endpoint:GET /v1/ledger/reconcile?date=YYYY-MM-DD -
P2Immutable ledger: DB trigger preventing UPDATE/DELETE ontransactions -
P2Merchant wallet top-up via Stripe PaymentIntent (stub → live)
-
P1GET /v1/drivers/me/wallet— accumulated credits, pending payout -
P1Payout request flow: driver initiates → ops approval → bank transfer record -
P2Weekly automated payout batch for partners above minimum threshold -
P2Tax withholding flag per driver registration profile -
P3Instant payout premium tier (fee surcharge)
-
P0Verify API key cannot read another merchant's transactions -
P1SUPERADMINledger dashboard with tenant filter -
P1Regional Manager read-only wallet summaries aggregated by hub -
P2Low-balance alert webhook for merchants below configurable threshold -
P2Credit line support for enterprise merchants (ff_live_merchant_enterprise_9c2a5d1btier)
Goal: Continuous verification across unit, integration, E2E, smoke, and mobile widget layers — mapped directly to PRD acceptance criteria.
Business value: Prevents regression in matching logic, RBAC scoping, and merchant order flows during rapid multi-repo development.
-
P0Jest unit config (test/jest-unit.json) -
P0Geo-matching unit tests (Haversine accuracy, radius filter, closest selection) -
P0Pricing service unit tests (vehicle tier ordering) -
P0Health integration tests via Supertest (health.integration.spec.ts) -
P0RBAC integration tests (rbac.integration.spec.ts) -
P1Live stack smoke spec (stack-smoke.e2e.spec.ts) withQA_RUN_LIVE_STACKgate -
P1Auth login integration test with seededMERCHANT_ADMINuser -
P1Order create integration test with mocked Prisma + BullMQ -
P2Matching processor integration test with testcontainers Postgres + Redis
-
P0playwright.config.tswith Next.jswebServerauto-start on:3001 -
P0e2e/portal.spec.ts— home page and create form field visibility -
P0e2e/orders.spec.ts— full create → tracker flow with mocked API -
P1Jest unit test forextractApiErrorMessage(orders.test.ts) -
P1Playwright test against live API (optionalQA_RUN_LIVE_STACKmode) -
P1Visual regression baseline for order tracker step UI -
P2Accessibility audit (axe-playwright) on create order form -
P2RBAC login flow E2E forMERCHANT_ADMINJWT path
-
P0Widget test: login validation error on empty password (login_page_test.dart) -
P0Widget test: login navigation on valid credentials (login_page_test.dart) -
P0Widget test: job offer accept banner (job_offer_page_test.dart) -
P0Integration test: full driver login → accept job (integration_test/app_test.dart) -
P1Widget test: loading spinner state onlogin_buttonduring submit -
P1Integration test with mockdioagainstPOST /v1/auth/login -
P2Golden tests forLoginPageandJobOfferPagethemes -
P2Background location ping widget test withgeolocatormock
-
P0fleetflow-infra/qa/smoke-stack.mjs— API liveness, readiness, web portal HTTP 200 -
P0Root scripts:pnpm test:qa,pnpm test:qa:web,pnpm test:qa:flutter,pnpm test:smoke -
P1QA_TESTING.mdfull pyramid documentation -
P1GitHub Actions workflow:test:qaon every PR -
P1GitHub Actions workflow:test:smokeon merge tomainwith docker compose -
P2Prisma sync automation in CI (pnpm prisma:sync --seed) -
P2Test coverage reporting to PR comments
-
P1Link each PRD acceptance criterion to a test file inQA_TESTING.md -
P1Quarterly backlog grooming: close shipped items, re-prioritizeP0security tasks -
P2Chaos test: kill Redis mid-matching, verify order does not double-debit
| Epic | Shipped | Remaining | P0 Open |
|---|---|---|---|
| Epic 1: RBAC | 8 | 17 | 0 |
| Epic 2: Dispatch | 7 | 18 | 1 |
| Epic 3: Ledger | 6 | 14 | 1 |
| Epic 4: QA | 16 | 14 | 0 |
| Total | 37 | 63 | 2 |
Grooming notes (2026-07-11): Focus next sprint on Epic 2.2 idempotent matching and Epic 3.2 balance re-read inside transaction — both are P0 ledger integrity hardening items before Bengkulu production pilot.