# Codebase Structure **Analysis Date:** 2026-03-16 ## Directory Layout ``` SimpleFinanceDash/ ├── src/ # All application source code │ ├── main.tsx # React 19 app entry point with providers │ ├── App.tsx # Route configuration and guards │ ├── index.css # Global Tailwind styles │ ├── pages/ # Page components (routed views) │ ├── components/ # Reusable and layout components │ │ └── ui/ # Shadcn/Radix UI primitives (16 components) │ ├── hooks/ # Custom data-fetching hooks (TanStack Query) │ ├── lib/ # Utilities, types, configuration │ └── i18n/ # Internationalization setup and resources ├── supabase/ # Supabase project files │ └── migrations/ # Database schema migrations ├── public/ # Static assets ├── index.html # HTML entry point for Vite ├── package.json # Dependencies and build scripts ├── vite.config.ts # Vite bundler configuration ├── tsconfig.json # TypeScript base configuration ├── tsconfig.app.json # App-specific TypeScript config ├── tsconfig.node.json # Build script TypeScript config ├── eslint.config.js # ESLint configuration ├── components.json # Shadcn CLI component registry ├── .env.example # Example environment variables template └── .gitignore # Git ignore rules ``` ## Directory Purposes **`src/pages/`:** - Purpose: Page-level components that correspond to routes in App.tsx - Contains: 9 page components (all .tsx) - Key files: - `DashboardPage.tsx` (316 lines) - Monthly budget dashboard with charts - `BudgetDetailPage.tsx` (555 lines) - Detailed budget editing and item management - `TemplatePage.tsx` (459 lines) - Monthly budget template editor - `BudgetListPage.tsx` (261 lines) - List of all budgets with quick actions - `CategoriesPage.tsx` (214 lines) - Category management (CRUD) - `QuickAddPage.tsx` (202 lines) - Quick-add library editor - `SettingsPage.tsx` (125 lines) - User preferences - `LoginPage.tsx` (107 lines) - Email/password and OAuth login - `RegisterPage.tsx` (81 lines) - User registration form Each page follows pattern: - Imports hooks at top - Calls hooks in component body - Renders UI from state - Delegates complex logic to sub-components **`src/components/`:** - Purpose: Reusable UI components and layout wrappers - Contains: Custom components + UI library primitives - Key files: - `AppLayout.tsx` - Sidebar wrapper for authenticated pages - `QuickAddPicker.tsx` - Multi-modal quick-add workflow component - `ui/` - 16 Shadcn-based components (Button, Dialog, Select, Table, etc.) **`src/hooks/`:** - Purpose: Encapsulate all server communication and state queries - Contains: 6 custom hooks - Key files: - `useAuth.ts` - Session management and auth operations (signUp, signIn, signOut) - `useBudgets.ts` - Budget CRUD, item management, template generation - `useCategories.ts` - Category CRUD operations - `useTemplate.ts` - Monthly budget template management - `useQuickAdd.ts` - Quick-add item library CRUD - `use-mobile.ts` - Responsive breakpoint detection utility Each hook: - Defines typed query keys as const arrays - Initializes useQuery/useMutation from TanStack Query - Returns { data, loading, ...mutations } - Implements onSuccess cache invalidation **`src/lib/`:** - Purpose: Core utilities, types, and configuration - Contains: 5 files - Key files: - `types.ts` - TypeScript interfaces: Profile, Category, Budget, BudgetItem, Template, TemplateItem, QuickAddItem - `supabase.ts` - Supabase client creation with environment validation - `palette.ts` - Category color constants (CSS variables) and labels (en/de) - `format.ts` - Currency formatting with Intl.NumberFormat API - `utils.ts` - General helpers (like cn for class merging) **`src/i18n/`:** - Purpose: Internationalization setup and resource files - Contains: `index.ts` and JSON translation files - Key files: - `index.ts` - i18next initialization with react-i18next bindings - `en.json` - English translation strings (namespaced by feature) - `de.json` - German translation strings - Initialized at app startup before any React render - Provides `useTranslation()` hook for all components **`src/components/ui/`:** - Purpose: Unstyled, accessible UI primitives from Shadcn and Radix UI - Contains: 16 files of component exports - Includes: Badge, Button, Card, Dialog, Dropdown Menu, Input, Label, Popover, Select, Separator, Sheet, Sidebar, Skeleton, Table, Tooltip, Sonner Toast wrapper - Pattern: Each wraps Radix primitive with Tailwind styling - Do NOT modify these files — regenerate via Shadcn CLI if needed ## Key File Locations **Entry Points:** - `src/main.tsx` - DOM mount point, providers initialization - `src/App.tsx` - Route definitions and authentication guards - `index.html` - Vite HTML template with root div **Configuration:** - `vite.config.ts` - Build tooling (React plugin, Tailwind vite plugin, @ alias) - `tsconfig.json` - Base TS config with @ path alias - `eslint.config.js` - Linting rules - `components.json` - Shadcn CLI registry - `package.json` - Dependencies: react@19, react-router-dom@7, @tanstack/react-query@5, @supabase/supabase-js@2, i18next, lucide-react, recharts, tailwindcss@4, sonner **Core Logic:** - `src/hooks/useBudgets.ts` - Largest hook (369 lines) with factory pattern for detail queries - `src/hooks/useTemplate.ts` - Template mutations with sort_order management - `src/lib/types.ts` - Single source of truth for domain types - `src/lib/supabase.ts` - Client configuration (2 lines of config + validation) **Testing:** - No test files present (no `*.test.ts`, `*.spec.ts`) - No jest.config.js or vitest.config.ts ## Naming Conventions **Files:** - Pages: PascalCase with "Page" suffix (`DashboardPage.tsx`) - Hooks: camelCase with "use" prefix (`useAuth.ts`, `useBudgets.ts`) - Components: PascalCase (`AppLayout.tsx`, `QuickAddPicker.tsx`) - Utilities: camelCase descriptive (`format.ts`, `palette.ts`) - Types: camelCase file, PascalCase exports (`types.ts` exports `interface Budget`) - UI components: kebab-case file, PascalCase export (`card.tsx` exports `Card`) **Directories:** - Feature folders: lowercase plural (`src/hooks/`, `src/pages/`, `src/components/`) - UI library: `ui/` subfolder under components **Functions & Variables:** - Functions: camelCase (`formatCurrency`, `useBudgets`) - Component functions: PascalCase (`DashboardPage`, `QuickAddPicker`) - Constants: UPPER_SNAKE_CASE (`CATEGORY_TYPES`, `EXPENSE_TYPES`) - Variables: camelCase (`budgetId`, `categoryId`, `isSaving`) **Types:** - Interfaces: PascalCase (`Budget`, `BudgetItem`) - Type unions: PascalCase (`CategoryType`) - Props interfaces: PascalCase ending with "Props" (`QuickAddPickerProps`) ## Where to Add New Code **New Feature (e.g., Reports):** 1. Create page: `src/pages/ReportsPage.tsx` 2. Create hook: `src/hooks/useReports.ts` with query keys and mutations 3. Add types: `src/lib/types.ts` - add new interfaces (Report, ReportItem) 4. Add route: `src/App.tsx` - add Route element 5. Add nav link: `src/components/AppLayout.tsx` - add to navItems array 6. Add i18n: `src/i18n/en.json` and `src/i18n/de.json` - add new keys **New Component (e.g., CategoryBadge):** - If simple display component: `src/components/CategoryBadge.tsx` - If UI primitive wrapper: `src/components/ui/category-badge.tsx` (follow shadcn pattern) - Composition: Import from ui/ folder, layer styling via className **New Utility Function:** - General helpers: `src/lib/utils.ts` - Domain-specific (e.g., budget math): Add to relevant hook file or create `src/lib/budgetHelpers.ts` - Formatting logic: `src/lib/format.ts` **New Hook:** - Data fetching: `src/hooks/useFeatureName.ts` - Pattern: Export named function, define query keys, use useQuery/useMutation, return typed object - Example structure from `useTemplate.ts`: - Query keys at top (const) - Helper functions (async functions) - Main hook function with useQuery/useMutation setup - Exposed API object return **Styling:** - Component styles: Tailwind className in JSX (no CSS files) - Global styles: `src/index.css` (imports Tailwind directives) - Color system: CSS variables in theme (Tailwind config) - Category colors: `src/lib/palette.ts` (maps to CSS var(--color-X)) ## Special Directories **`src/components/ui/`:** - Purpose: Shadcn registry of unstyled, accessible Radix UI components - Generated: Via `npx shadcn-ui@latest add [component]` - Committed: Yes (production code) - Do NOT hand-edit — regenerate if Shadcn updates **`public/`:** - Purpose: Static assets (favicon, images, fonts) - Generated: No - Committed: Yes - Served at root by Vite **`supabase/migrations/`:** - Purpose: Database schema as versioned SQL files - Generated: Via Supabase CLI - Committed: Yes (tracked via git) - Applied: By `supabase db push` command **`.env` files:** - Purpose: Runtime configuration (Supabase URL, API key) - Generated: Via `.env.example` template - Committed: NO — in .gitignore - Required for: Local dev and CI/CD **`dist/`:** - Purpose: Production bundle output - Generated: Via `npm run build` - Committed: No — in .gitignore - Deployment: Upload contents to CDN or web server ## Code Organization Principles **Vertical Slices:** - Feature → Page → Hook → Library - Minimizes cross-feature coupling - Easy to add/remove features **Co-location of Related Code:** - Page component near its hooks - Query keys defined in same hook as queries - Mutations and queries in same hook for domain entity **Type Safety:** - All Supabase queries cast return value to TypeScript type - TanStack Query generic parameters: `useQuery()` and `useMutation()` - Props interfaces for all custom components **Consistent Hook Patterns:** - All data hooks follow: query setup → mutations setup → return typed object - Mutations always have onSuccess cache invalidation - Query keys are hierarchical arrays enabling granular invalidation --- *Structure analysis: 2026-03-16*