Files

11 KiB

phase, plan, type, wave, depends_on, files_modified, autonomous, requirements, must_haves
phase plan type wave depends_on files_modified autonomous requirements must_haves
01-foundation-dashboard 04 execute 3
01-01
01-02
01-03
src/app/components/Sidebar.tsx
src/app/components/LoginIndicator.tsx
src/app/components/Navigation.tsx
src/app/routes.ts
vite.config.ts
.bundlesize.json
src/app/components/__tests__/Sidebar.test.tsx
src/app/components/__tests__/LoginIndicator.test.tsx
true
DASH-07
UI-02
UI-03
UI-04
UI-05
truths artifacts key_links
Sidebar navigation has Settings, Calibration, Flash Memory links
Login indicator shows logged-in state
Bundle size is under 170KB (target) / 200KB (limit)
All routes defined and working
Touch-friendly navigation (44px+ targets)
path provides exports min_lines
src/app/components/Sidebar.tsx Navigation sidebar Sidebar 50
path provides exports
src/app/components/LoginIndicator.tsx Login status indicator LoginIndicator
path provides exports
src/app/routes.ts Route definitions router
path provides
.bundlesize.json Bundle size budget config
from to via
Sidebar routes.ts Link components
from to via
LoginIndicator Header Header composition
from to via
routes.ts RainfallView Route configuration
Complete the dashboard with navigation, login indicator, route configuration, and verify performance budget (<170KB bundle size).

Purpose: Navigation provides access to other sections (Settings, Calibration, Flash Memory). Login indicator shows authentication status. Performance verification ensures Pi Zero 2 W compatibility.

Output: Working navigation, login indicator, routes configured, bundle size verified under budget.

<execution_context> @./.opencode/get-shit-done/workflows/execute-plan.md @./.opencode/get-shit-done/templates/summary.md </execution_context>

@.planning/phases/01-foundation-dashboard/01-CONTEXT.md @.planning/phases/01-foundation-dashboard/01-RESEARCH.md @sample_interface/src/app/components/Sidebar.tsx @sample_interface/src/app/routes.ts

Key Implementation Details

Navigation Items:

  • Dashboard (home)
  • Settings (with sub-items)
  • Calibration
  • Flash Memory

Sidebar Design:

  • Fixed width (64px icons-only or 240px expanded)
  • Touch-friendly items (44px+ height)
  • Active state highlighting
  • Collapsible on mobile

Login Indicator:

  • Green dot/icon when logged in
  • Gray/red when logged out
  • Text label: "Logged In" / "Logged Out"
  • Small and compact for header

Routes:

  • / → Dashboard (RainfallView)
  • /utility/* → Settings (placeholder for Phase 2)
  • /calibration → Calibration (placeholder)
  • /flash-memory → Flash Memory (placeholder)

Bundle Size Budget:

  • Target: <170KB gzipped initial JS
  • Limit: <200KB gzipped
  • Tools: bundlesize, rollup-plugin-analyzer
task 1: Create LoginIndicator component src/app/components/LoginIndicator.tsx, src/app/components/__tests__/LoginIndicator.test.tsx - Shows green status when isLoggedIn=true - Shows gray/red status when isLoggedIn=false - Compact size for header placement - Accessible (aria-label) 1. Create src/app/components/LoginIndicator.tsx: - Props: isLoggedIn (boolean), className (optional) - Use shadcn/ui Badge or custom indicator - Logged in: Green dot + "Logged In" text - Logged out: Gray dot + "Login" text - Compact: h-6, text-xs - Use Lucide User icon - Add aria-label for accessibility
2. Create tests:
   - Shows correct state for logged in/out
   - Has accessible label
   - Accepts custom className
npm test -- --run LoginIndicator 2>&1 | grep -E "(PASS|FAIL|✓|✗)" LoginIndicator with accessible states created task 2: Update Sidebar navigation src/app/components/Sidebar.tsx, src/app/components/__tests__/Sidebar.test.tsx - Shows Dashboard, Settings, Calibration, Flash Memory links - Touch-friendly items (44px+ height) - Active state for current route - Collapsible sections 1. Update src/app/components/Sidebar.tsx: - Import NavLink from react-router - Define navigation items array: * Dashboard (Home icon) → / * Settings (Settings icon) → /utility * Calibration (Gauge icon) → /calibration * Flash Memory (HardDrive icon) → /flash-memory - Map items to NavLink components - Item height: min-h-[44px] - Active state: bg-accent class - Icon + label layout - Collapsible on mobile with hamburger
2. Create tests:
   - Renders all navigation items
   - Items have correct links
   - Touch target size adequate
   - Active state applied correctly
npm test -- --run Sidebar 2>&1 | grep -E "(PASS|FAIL|✓|✗)" Sidebar with 4 navigation items created task 3: Configure routes for all views src/app/routes.ts, src/app/components/views/SettingsView.tsx, src/app/components/views/CalibrationView.tsx, src/app/components/views/FlashMemoryView.tsx - All routes defined in routes.ts - Settings, Calibration, Flash Memory have placeholder views - Routes use lazy loading where appropriate - Navigation between routes works 1. Create placeholder views: - src/app/components/views/SettingsView.tsx: "Settings - Phase 2" placeholder - src/app/components/views/CalibrationView.tsx: "Calibration - Phase 3" placeholder - src/app/components/views/FlashMemoryView.tsx: "Flash Memory - Phase 3" placeholder
2. Update src/app/routes.ts:
   - Import all views
   - Define routes array:
     * path: "/", element: RainfallView
     * path: "/utility/*", element: SettingsView
     * path: "/calibration", element: CalibrationView
     * path: "/flash-memory", element: FlashMemoryView
   - Use createBrowserRouter
   - Add error boundary for 404s
grep -n "SettingsView\|CalibrationView\|FlashMemoryView" src/app/routes.ts 2>/dev/null | head -10 Routes configured for all 4 main sections task 4: Integrate LoginIndicator into Header src/app/components/Header.tsx - Header displays LoginIndicator - Gets login state from sensor store - Compact placement in header row 1. Update src/app/components/Header.tsx: - Import LoginIndicator - Get isLoggedIn from sensor store (or mock for now) - Place LoginIndicator in header layout - Ensure proper spacing and alignment
2. Test integration:
   - Login indicator visible in header
   - Updates when login state changes
grep -n "LoginIndicator" src/app/components/Header.tsx 2>/dev/null | head -5 LoginIndicator integrated into Header task 5: Configure bundle size checking .bundlesize.json, vite.config.ts, package.json - Bundle size limit configured (170KB target, 200KB max) - Build fails if bundle exceeds limit - Size checking integrated in CI 1. Create .bundlesize.json: ```json { "files": [ { "path": "dist/assets/*.js", "maxSize": "200kb", "compression": "gzip" } ] } ```
2. Update package.json scripts:
   - "build:check": "npm run build && bundlesize"
   - Add bundlesize as devDependency
   
3. Update vite.config.ts for optimization:
   - Manual chunks for vendor code
   - Drop console in production
   - Minification settings
   
4. Install bundlesize: `pnpm add -D bundlesize`
test -f .bundlesize.json && echo "Config exists" || echo "Config missing" Bundle size checking configured task 6: Build and verify bundle size dist/ - Production build succeeds - Bundle size under 200KB limit - Ideally under 170KB target - No build errors or warnings 1. Run production build: - `npm run build` - Check for errors
2. Analyze bundle size:
   - `npm run build:check` or check dist/ folder
   - Look at main JS file size
   - Use rollup-plugin-visualizer if needed
   
3. If over budget, investigate:
   - Run `npx vite-bundle-visualizer`
   - Identify large dependencies
   - Consider code splitting
   
4. Document actual size in SUMMARY
ls -lh dist/assets/*.js 2>/dev/null | awk '{print $5, $9}' | head -5 Bundle built and size verified (target: <170KB, limit: <200KB) task 7: Final integration test src/app/App.tsx - Full app renders without errors - Navigation works between routes - Dashboard shows all data - No console errors 1. Verify App.tsx integration: - RouterProvider with routes - DashboardLayout with Header and Sidebar - Outlet for route content
2. Run all tests:
   - `npm test` — should pass
   
3. Verify no TypeScript errors:
   - `npx tsc --noEmit`
   
4. Check for console errors:
   - Review any warnings in test output
npm test 2>&1 | tail -5 Full integration verified, all tests passing After completing all tasks: 1. Run `npm test` — all tests should pass 2. Run `npm run build` — should succeed 3. Verify bundle size: Check dist/ folder, should be <200KB 4. Check routes: `grep -r "path:" src/app/routes.ts | wc -l` should be 4+ 5. Verify navigation: `grep -r "NavLink\|Link" src/app/components/Sidebar.tsx` 6. Check LoginIndicator in Header: `grep "LoginIndicator" src/app/components/Header.tsx`

<success_criteria>

  • LoginIndicator component shows logged-in state
  • Sidebar has navigation to Settings, Calibration, Flash Memory
  • All routes configured and working
  • Bundle size under 200KB (target <170KB)
  • No TypeScript errors
  • All tests passing
  • Full app integrates without errors </success_criteria>
After completion, create `.planning/phases/01-foundation-dashboard/01-04-SUMMARY.md`