3.9 KiB
3.9 KiB
TimeToLeave — Implementation Checklist
Source: REWRITE_PLAN.md Total: 4 phases, 14 steps, ~5 hours estimated effort
Phase 1 — Unblock Runtime (~45 min)
Fix bugs that crash the app or lose user data.
| Step | ✅ Implemented | ✔️ Reviewed | Notes |
|---|---|---|---|
Step 1: Fix SSR Crash in useBikeRoute (~10 min) |
[x] | [x] | Relative URL fetch replaces window.location.href — SSR-safe. isMounted guard intact. |
Step 2: Wire Calendar Events into EventsStore (~15 min) |
[x] | [x] | CalendarPanel.tsx merges via useEffect when calendar events arrive. mergeEvents() converts CalendarEvent (string eventTime) → Event (Date eventTime). Bonus: localStorage persistence with rehydration. |
Step 3: Add Input Validation to /api/hafas (~20 min) |
[x] | [x] | Validates svcReqL array shape, method allowlist (TripSearch/LocMatch), caps numF at 10. Extra type guard on svcReq.meth (typeof svcReq.meth !== 'string') exceeds spec. |
Phase 2 — Deduplicate Code (~2 hours)
Eliminate duplicated logic so each integration has one source of truth.
| Step | ✅ Implemented | ✔️ Reviewed | Notes |
|---|---|---|---|
| Step 4: Consolidate HAFAS Journey Parsing (~40 min) | [x] | [x] | parseHafasJourneys moved to hafas-client.ts, exported, imported by useJourneys.ts. Option A followed. |
| Step 5: Wire API Routes to Use Library Clients (~30 min) | [x] | [x] | Both routes use module-level singleton clients. Param validation, error handling, and try/catch intact. |
| Step 6: Remove Dead Code (~5 min) | [x] | [x] | live-status-utils.ts deleted, export removed from index.ts. No remaining references. |
| Step 7: Create Missing Test Setup File (~10 min) | [x] | [x] | src/test/setup.ts created with jest-dom vitest import. Referenced correctly in vitest.config.ts. |
Phase 3 — Performance & UX (~1.5 hours)
| Step | ✅ Implemented | ✔️ Reviewed | Notes |
|---|---|---|---|
| Step 8: Add Debounce to Lookup Hooks (~25 min) | [x] | [x] | 400ms setTimeout + AbortController in useGeocode.ts and useDestinationStation.ts. AbortError silently ignored. |
| Step 9: Pre-Group Calendar Events by Date (~20 min) | [x] | [x] | useMemo builds Map<string, Event[]> keyed by YYYY-MM-DD. Per-cell filter() replaced with O(1) map lookup. |
| Step 10: Add Dark Mode Toggle (~20 min) | [x] | [x] | useTheme.ts created (localStorage + prefers-color-scheme). Sun/moon toggle button added to Header.tsx. |
| Step 11: Fix Bike Route Steps (~5 min) | [x] | [x] | steps: "true" already present in BikeRoutingClient.getBikeRoute() query params. |
Phase 4 — Monitoring & Testing (~1 hour)
| Step | ✅ Implemented | ✔️ Reviewed | Notes |
|---|---|---|---|
| Step 12: Add Correlation IDs to API Errors (~15 min) | [x] | [x] | randomUUID().slice(0, 8) in catch blocks of bike-route, geocode, hafas, calendar, calendar/parse. Logged server-side, returned in JSON. Existing API tests updated to assert correlationId. |
| Step 13: Add Hook Tests (~30 min) | [x] | [x] | useJourneys.test.ts (4 tests: no-op when missing IDs, success, HTTP error, fetch throw). useBikeRoute.test.ts (4 tests: no-op when missing coords, success, HTTP error, fetch throw). |
| Step 14: Add Component Tests (~15 min) | [x] | [x] | EventCard.test.tsx (renders title + destination, hooks mocked). CalendarView.test.tsx (3 tests: month header, event on correct day, overflow indicator). |
Summary
| Phase | Steps | Est. Time |
|---|---|---|
| 1 — Unblock Runtime | 1–3 | ~45 min |
| 2 — Deduplicate Code | 4–7 | ~2 hours |
| 3 — Performance & UX | 8–11 | ~1.5 hours |
| 4 — Monitoring & Testing | 12–14 | ~1 hour |
| Total | 14 | ~5 hours |