# Splitwise Application - Code Plan This document outlines the technical architecture, stack, and implementation plan for our Splitwise-style expense-splitting application. ## Tech Stack ### Frontend - **Runtime**: Bun - **Framework**: React 18+ with TypeScript - **Build Tool**: Vite - **Styling**: TailwindCSS with Shadcn UI component library - **State Management**: Zustand - **Data Fetching**: TanStack Query (React Query) - **Form Handling**: React Hook Form with Zod validation - **Routing**: React Router v6 - **Testing**: Vitest, React Testing Library - **Components**: Shadcn UI (customizable Radix UI-based components) ### Backend - **Runtime**: Bun - **Language**: TypeScript - **Framework**: Hono (lightweight, fast, TypeScript-first) - **Database**: PostgreSQL - **ORM**: Drizzle (TypeScript-first ORM) - **Authentication**: better-auth (framework-agnostic authentication with email/password and social sign-on) - **Validation**: Zod - **File Storage**: Local storage with Sharp for image processing (can be migrated to S3 later) - **Testing**: Bun test ## Architecture Overview We'll implement a clean architecture with separation of concerns: ### Frontend Architecture - **Application Layer**: React components, hooks, and contexts - **Domain Layer**: Zustand stores and business logic - **Infrastructure Layer**: API clients and external service integrations #### Key Frontend Modules: 1. **Auth Module**: Sign-up, sign-in, profile management 2. **Expenses Module**: Create, edit, delete expenses 3. **Settlements Module**: Balances, settle up functionality 4. **Activity Module**: Feed of expense and settlement activities 5. **Notifications Module**: In-app notifications 6. **Settings Module**: User preferences and application settings ### Backend Architecture - **API Layer**: Hono routes and controllers - **Service Layer**: Business logic and core application services - **Data Access Layer**: Drizzle ORM models and repositories - **Domain Layer**: Entity definitions and domain logic #### Key Backend Modules: 1. **Auth Module**: User authentication and authorization 2. **Users Module**: User management and profiles 3. **Contacts Module**: Contact relationships and invitations 4. **Expenses Module**: Expense tracking and splits 5. **Settlements Module**: Balance calculations and settlements 6. **Notifications Module**: Notification generation and delivery 7. **Files Module**: Receipt image upload and processing ## Database Schema (Initial) ### Users - id: uuid (primary key) - email: string (unique) - display_name: string - profile_photo_url: string (nullable) - default_currency: string (default: 'USD') - locale: string (default: 'en-US') - timezone: string (default: 'UTC') - created_at: timestamp - updated_at: timestamp ### Auth (managed by better-auth) - id: uuid (primary key) - user_id: uuid (foreign key -> Users.id) - provider: string (e.g., 'email', 'google', 'github') - provider_user_id: string (nullable, for social providers) - email: string - password_hash: string (nullable, for email provider) - refresh_token: string (nullable) - last_login: timestamp - created_at: timestamp - updated_at: timestamp ### Contacts - id: uuid (primary key) - user_id: uuid (foreign key -> Users.id) - contact_id: uuid (foreign key -> Users.id) - status: enum ('pending', 'accepted', 'declined') - created_at: timestamp - updated_at: timestamp ### Expenses - id: uuid (primary key) - title: string - amount: decimal - date: timestamp - payer_id: uuid (foreign key -> Users.id) - memo: text (nullable) - receipt_image_url: string (nullable) - created_at: timestamp - updated_at: timestamp ### ExpenseParticipants - id: uuid (primary key) - expense_id: uuid (foreign key -> Expenses.id) - user_id: uuid (foreign key -> Users.id) - share_amount: decimal - created_at: timestamp - updated_at: timestamp ### Settlements - id: uuid (primary key) - payer_id: uuid (foreign key -> Users.id) - receiver_id: uuid (foreign key -> Users.id) - amount: decimal - date: timestamp - memo: text (nullable) - created_at: timestamp - updated_at: timestamp ### Notifications - id: uuid (primary key) - user_id: uuid (foreign key -> Users.id) - type: enum ('expense_added', 'expense_edited', 'settlement_received') - content: jsonb - is_read: boolean (default: false) - created_at: timestamp ## API Endpoints ### Authentication (managed by better-auth) - POST /api/auth/register - POST /api/auth/login - POST /api/auth/social/:provider - POST /api/auth/social/:provider/callback - POST /api/auth/logout - GET /api/auth/me - POST /api/auth/refresh-token - POST /api/auth/forgot-password - POST /api/auth/reset-password ### Users - GET /api/users/profile - PUT /api/users/profile - PUT /api/users/settings ### Contacts - GET /api/contacts - POST /api/contacts - PUT /api/contacts/:id - DELETE /api/contacts/:id ### Expenses - GET /api/expenses - POST /api/expenses - GET /api/expenses/:id - PUT /api/expenses/:id - DELETE /api/expenses/:id - POST /api/expenses/:id/receipt ### Balances - GET /api/balances - GET /api/balances/:contactId ### Settlements - POST /api/settlements - GET /api/settlements - GET /api/settlements/:id ### Notifications - GET /api/notifications - PUT /api/notifications/:id/read - PUT /api/notifications/read-all ## Implementation Plan ### Phase 1: Project Setup 1. Initialize frontend and backend projects with Bun 2. Set up TypeScript configuration 3. Configure Vite for the frontend 4. Install and configure Shadcn UI with TailwindCSS 5. Set up Hono for the backend 6. Configure Drizzle ORM with PostgreSQL 7. Set up development environment with Docker for database ### Phase 2: Core Authentication 1. Install and configure better-auth library 2. Set up authentication adapters for Hono and PostgreSQL 3. Configure email/password and social sign-on providers 4. Create authentication forms on frontend 5. Implement profile management ### Phase 3: Expense Tracking 1. Implement expense CRUD operations on backend 2. Create expense form components on frontend 3. Implement expense splitting logic 4. Add receipt image upload functionality ### Phase 4: Balances and Settlements 1. Implement balance calculation logic 2. Create settlement endpoints 3. Build balance visualization components 4. Implement settlement UI ### Phase 5: Activity Feed and Notifications 1. Create activity tracking for expenses and settlements 2. Implement notification generation 3. Build activity feed UI 4. Add in-app notification components ### Phase 6: Settings and Refinement 1. Implement user settings 2. Add locale and currency formatting 3. Refine UI/UX 4. Performance optimizations ## Folder Structure ### Frontend ``` frontend/ ├── public/ ├── src/ │ ├── assets/ │ ├── components/ │ │ ├── auth/ │ │ ├── expenses/ │ │ ├── settlements/ │ │ ├── activity/ │ │ ├── notifications/ │ │ ├── settings/ │ │ └── ui/ │ ├── hooks/ │ │ └── useBetterAuth.ts │ ├── pages/ │ ├── services/ │ │ ├── api.ts │ │ └── auth.ts │ ├── stores/ │ ├── types/ │ ├── utils/ │ ├── lib/ │ │ └── shadcn-ui/ │ ├── styles/ │ │ └── globals.css │ ├── App.tsx │ └── main.tsx ├── components.json ├── tailwind.config.js ├── .env ├── package.json └── tsconfig.json ``` ### Backend ``` backend/ ├── src/ │ ├── controllers/ │ ├── db/ │ │ ├── schema/ │ │ └── migrations/ │ ├── middleware/ │ ├── services/ │ ├── auth/ │ │ ├── config.ts │ │ ├── providers/ │ │ └── adapters/ │ ├── types/ │ ├── utils/ │ └── index.ts ├── .env ├── package.json └── tsconfig.json ``` ## Getting Started ### Prerequisites - Bun installed - PostgreSQL database - Node.js 18+ (for additional tools) ### Setup Instructions 1. Clone the repository 2. Install dependencies for both frontend and backend with `bun install` 3. Set up environment variables (.env files) 4. Run database migrations with Drizzle 5. Start the development servers: - Frontend: `bun run dev` - Backend: `bun run dev` ## Development Practices - TypeScript for type safety - Feature branch workflow - Write tests for critical functionality - Use Zod schemas for validation and type inference - Follow REST principles for API design - Document API endpoints with JSDoc or Swagger