Phase 8 — Mobile + PWA
Status: Shipped ✅ · Owner: Frontend Lead · Duration: 2 weeks · Gate: G8
1. Overview
Phase 8 makes Atlas first-class on mobile without shipping a native app. It hardens the responsive layouts, ships a true Progressive Web App (installable, push-capable, offline-capable for inspection work), implements mobile-specific UX for the highest-value flows (work-order execution, asset lookup, approvals, AI chat), and prepares for a future native shell (Capacitor) if needed.
2. Objectives
- O8.1 — Every primary screen is responsive and usable on 360-px-wide phones.
- O8.2 — PWA installable on iOS Safari and Android Chrome; manifest, icons, splash, theming correct.
- O8.3 — Service worker enables offline mode for: viewing recent work orders, executing an inspection checklist offline, syncing on reconnect.
- O8.4 — Push notifications working (Web Push via VAPID).
- O8.5 — Mobile-specific UX for work order execution (camera capture, signature, barcode/QR scan via WebRTC + jsQR).
- O8.6 — Approval inbox optimised for mobile (single-tap approve/reject, swipe actions).
- O8.7 — Mobile dashboard view (read-only) with widget-by-widget vertical scroll.
- O8.8 — Performance budget on mobile: LCP < 3s on 4G, Lighthouse mobile score ≥ 90 on the main routes.
3. Scope
3.1 In-scope
- Audit every existing screen for mobile breakage; fix.
- PWA manifest (
/public/manifest.webmanifest); icons (192x192,512x512, maskable); splash for iOS. - Service worker: precache shell, runtime cache for assets, IndexedDB for offline data.
- Offline mode: work-order detail cached on view; inspection checklist completable offline; queued sync.
- Web Push: VAPID keys; subscribe flow; backend dispatcher; tenant-scoped.
- Mobile UX: camera capture (
<input type="file" capture>), signature pad, barcode/QR viaBarcodeDetectorAPI with jsQR fallback. - Mobile dashboard renderer (collapses widgets vertically; preserves theme).
- Mobile approvals inbox with swipe gestures.
- Accessibility on mobile (touch targets ≥ 44px).
- Bottom navigation for primary actions on mobile.
3.2 Out-of-scope
- Native shell with Capacitor (planned post-launch if PWA isn't enough).
- App Store / Play Store distribution.
- Background geolocation tracking.
- Voice notes (post-launch).
4. Dependencies
- Phase 2 (shell, themes), Phase 4 (modules), Phase 5 (dashboards), Phase 7 (approvals).
5. Architecture & Design
5.1 PWA stack
next-pwaor hand-rolled service worker (manifest + sw.js).- Workbox strategies:
- CacheFirst for static assets (icons, fonts, images).
- NetworkFirst for API GET requests with 24h fallback cache.
- StaleWhileRevalidate for module list pages.
- NetworkOnly for mutating requests.
- Offline queue: writes during offline persisted to IndexedDB; replayed on reconnect with conflict detection (
If-Matchheader).
5.2 Push notifications
- VAPID keys per environment (env vars).
- Subscribe flow on Settings → Notifications.
- Backend dispatcher (BullMQ worker) sends through Web Push API.
- Topics: aligned with notification categories from Phase 4.
- iOS Safari requires iOS 16.4+ for Web Push.
5.3 Mobile UX patterns
- Bottom nav (mobile only): Home / Tasks / Inbox / Search / Me.
- Sticky action bar on detail screens (primary action large, always reachable).
- Pull to refresh on list screens (custom hook; no library).
- Skeleton loaders for slow networks.
- Swipe actions on list items (approve/dismiss/snooze).
- Camera + scan: dedicated component used by inspection flow.
5.4 Offline inspection flow
- Technician opens a work order while online → cached.
- Technician enters inspection mode → checklist + form persisted to IndexedDB.
- Submits offline → queued with stable client ID.
- On reconnect → replayed; conflicts (item changed server-side) surfaced for resolution.
6. Detailed Specifications
6.1 PWA manifest
{
"name": "Atlas",
"short_name": "Atlas",
"start_url": "/",
"display": "standalone",
"background_color": "#0b0d12",
"theme_color": "#1F2A44",
"icons": [
{"src":"/icons/icon-192.png","sizes":"192x192","type":"image/png"},
{"src":"/icons/icon-512.png","sizes":"512x512","type":"image/png"},
{"src":"/icons/icon-maskable.png","sizes":"512x512","type":"image/png","purpose":"maskable"}
]
}
6.2 API additions
POST /api/v1/push/subscribe (store endpoint + keys)
DELETE /api/v1/push/subscribe/:id
POST /api/v1/sync/replay (offline queue replay)
6.3 Mobile dashboard rendering
- Mobile renderer ignores
layout.x/y/w/hand stacks widgets vertically bylayout.yorder, full width. - TV / War Room modes are explicitly desktop-only; mobile shows a message + the standard mobile view if user navigates there.
6.4 Performance budgets
- LCP < 3s on 4G simulation for
/,/work-orders,/dashboards/:id. - CLS < 0.1 on all routes.
- JS payload on first load < 250KB gzipped per route (route-split).
- Lighthouse mobile: Performance ≥ 90, Accessibility ≥ 95, Best Practices ≥ 95, PWA = installable.
7. Implementation Tasks
Epic 8.A — Responsive audit & fix
- 8.A.1 Audit every existing route at 360 / 414 / 768 widths; file issues.
- 8.A.2 Fix layout breakages.
- 8.A.3 Mobile-specific bottom nav.
Epic 8.B — PWA
- 8.B.1 Manifest + icons + splash.
- 8.B.2 Service worker + Workbox strategies.
- 8.B.3 Install prompt UX.
- 8.B.4 Background sync registration.
Epic 8.C — Offline
- 8.C.1 IndexedDB schema (work orders, checklists, queue).
- 8.C.2 Cache-on-view hook.
- 8.C.3 Offline inspection mode UI.
- 8.C.4 Replay + conflict resolution.
Epic 8.D — Push notifications
- 8.D.1 VAPID + subscribe flow.
- 8.D.2 Backend dispatcher.
- 8.D.3 Per-category preferences (Phase 4 prefs reused).
Epic 8.E — Mobile UX flows
- 8.E.1 Camera capture component.
- 8.E.2 Signature pad.
- 8.E.3 Barcode/QR scanner.
- 8.E.4 Work order execution flow (mobile).
- 8.E.5 Approvals inbox (mobile + swipe gestures).
- 8.E.6 AI chat mobile (full-screen, keyboard-aware).
Epic 8.F — Performance
- 8.F.1 Route-level code-splitting.
- 8.F.2 Image optimisation (next/image with sizes).
- 8.F.3 Font subsetting; preconnect.
- 8.F.4 Lighthouse CI gate.
8. Acceptance Criteria
- AC8.1 — On a 360-px-wide device, all primary screens render without horizontal scroll and with all actions reachable with thumb.
- AC8.2 — App installs to home screen on iOS Safari and Android Chrome; opens to standalone window.
- AC8.3 — In airplane mode, technician can view a previously-loaded work order, complete a checklist, and submit; on reconnect, the submission is replayed successfully.
- AC8.4 — Subscribing to push notifications and assigning a work order triggers a push within 10 seconds.
- AC8.5 — Camera capture, signature, and QR scan all work on iOS Safari and Android Chrome.
- AC8.6 — Mobile approvals inbox: swipe-right approves; swipe-left rejects; both create audit entries.
- AC8.7 — Lighthouse mobile audit scores ≥ 90 across the four metrics on
/and/work-orders. - AC8.8 — LCP < 3s on 4G simulation in Chrome devtools.
9. Test Requirements
- e2e on mobile viewport (Playwright with mobile emulation).
- Lighthouse CI gate.
- Manual device matrix: latest iPhone (Safari), Pixel (Chrome), iPad (Safari), one budget Android.
- Offline scenario tests.
- Push delivery tests with real endpoints (staged).
10. Documentation Requirements
docs/mobile/install.md.docs/mobile/offline.md.docs/mobile/push.md.docs/mobile/performance.md.- ADR-024: PWA-first vs Capacitor decision (publish current rationale).
11. Sign-off Criteria (Gate G8)
- All Acceptance Criteria met.
- Field walkthrough by a Kajima FM persona (or QA persona) — completing an inspection on a tablet without instructions.
- Frontend Lead, QA Lead, Product Owner sign
_gates/Gate_G8_signoff.md. - Tagged
phase-8-v1.0.
12. Risks & Mitigations
| Risk | L | I | Mitigation |
|---|---|---|---|
| iOS Web Push restrictions / iOS version coverage | 3 | 3 | Fall back to in-app + email; document minimum iOS. |
| Service worker cache leaking stale data | 3 | 3 | Versioned cache keys; cache-busting on deploy. |
| Offline conflict resolution UX confusing | 3 | 3 | Plain-language merge UI; default "server wins" with manual override. |
| Camera / scan permissions blocked by IT MDM | 2 | 3 | Document required permissions; provide manual entry fallback. |