# Aphoria Dashboard Quick Reference ## Project Path Configuration ### Where to Set It **Sidebar** → Bottom section → "Project Path" input The path persists in localStorage across page reloads. ### How Components Use It ```typescript import { useProjectPath } from "@/lib/hooks/useProjectPath"; function MyComponent() { const { projectPath, setProjectPath, isLoading } = useProjectPath(); // Use projectPath in API calls const result = await client.someOperation({ project_path: projectPath }); } ``` ### Storage Functions (Advanced) ```typescript import { getProjectPath, setProjectPath, clearProjectPath, hasCustomProjectPath } from "@/lib/project/storage"; // Direct localStorage access (usually not needed - use hook instead) const path = getProjectPath(); // Get from localStorage setProjectPath("/new/path"); // Save to localStorage clearProjectPath(); // Remove from localStorage const isCustom = hasCustomProjectPath(); // Check if custom path set ``` ## Component Patterns ### Scans Panel - No local path state - Uses `useProjectPath()` hook - Validates path before scanning - ScanForm displays path as read-only ### Claims Panel - No local path state - Uses `useProjectPath()` hook - Validates path before all operations (list, verify, coverage) - Shows path in card header ### Corpus Panel - Does NOT use project path (queries across all projects) - No changes needed ## Visual Indicators - **Green Dot (●)** in sidebar = custom path is set - **"Default path"** = using fallback default - **"Custom path"** = using localStorage value ## Error Handling All operations validate the path: ```typescript if (!projectPath.trim()) { setError("Please set a project path in the sidebar"); return; } ``` ## Environment Variables ```bash # Optional: Override default project path NEXT_PUBLIC_DEFAULT_PROJECT_PATH=/custom/default/path ``` Used when: 1. localStorage is empty (new user) 2. Server-side rendering (before localStorage available) ## Debugging ### Check localStorage in DevTools 1. Open DevTools → Application → Local Storage 2. Look for key: `aphoria-project-path` 3. Value shows current path ### Clear Stored Path ```javascript // In browser console: localStorage.removeItem('aphoria-project-path'); location.reload(); ``` ## Architecture ``` Storage Layer (SSR-safe): lib/project/storage.ts ↓ React Hook (Client-side): lib/hooks/useProjectPath.ts ↓ Components: - layout/sidebar.tsx (input) - scans/scans-panel.tsx (consumer) - claims/claims-panel.tsx (consumer) ``` ## Files Modified **Created:** - `src/lib/project/storage.ts` - localStorage persistence - `src/lib/hooks/useProjectPath.ts` - React hook **Modified:** - `src/components/layout/sidebar.tsx` - Project path input - `src/components/scans/scans-panel.tsx` - Use hook, remove local state - `src/components/scans/scan-form.tsx` - Display-only path - `src/components/claims/claims-panel.tsx` - Use hook, remove duplication ## Testing ### Unit Tests (Not Implemented Yet) ```typescript // Example test structure: describe('useProjectPath', () => { it('loads from localStorage on mount', () => {}); it('saves to localStorage on change', () => {}); it('returns empty string during SSR', () => {}); }); ``` ### E2E Tests (Not Implemented Yet) ```typescript test('project path persists across navigation', async ({ page }) => { await page.goto('/scans'); await page.fill('[placeholder="/path/to/project"]', '/test/path'); await page.goto('/claims'); // Verify path is still /test/path }); ``` ## Common Issues ### Issue: Path not persisting **Solution:** Check if localStorage is enabled in browser ### Issue: "Please set a project path in sidebar" **Solution:** Enter a valid path in sidebar input ### Issue: SSR hydration mismatch **Solution:** Hook uses `isLoading` state to avoid rendering path until client-side ### Issue: Default path not working **Solution:** Check `NEXT_PUBLIC_DEFAULT_PROJECT_PATH` env var or hardcoded default in storage.ts ## Future Enhancements See `PROJECT_PATH_IMPLEMENTATION.md` for: - Recent projects list - Project validation - Multi-project support - Project metadata storage