Wallet Wise is a full-stack MVP expense manager with a Progressive Web App frontend, Express API, Firestore-ready persistence, category budgets, dashboard analytics, and an AI chat assistant for spend queries and smart expense entry.
- Frontend: React + Vite + Tailwind CSS + Recharts
- Backend: Node.js + Express
- Database: Firebase Firestore with a local memory fallback for dev
- AI: Gemini API with structured intent extraction
- PWA:
vite-plugin-pwa
- Expense CRUD with amount, category, source, date, merchant, and note
- Dashboard with total spend, category breakdown, monthly trend, and recent transactions
- Category management with reusable icon and accent options
- Monthly budget tracking with >80% warning state
- AI chat for:
- spend summaries
- category/source queries
- budget risk checks
- natural-language expense entry
- Installable PWA with offline UI asset caching
wallet_wise/
├─ client/ # React + Vite + Tailwind PWA
│ ├─ public/
│ └─ src/
│ ├─ app/
│ ├─ components/
│ ├─ pages/
│ ├─ services/
│ ├─ store/
│ ├─ styles/
│ ├─ types/
│ └─ utils/
├─ server/ # Express API + AI orchestration + data adapters
│ └─ src/
│ ├─ config/
│ ├─ lib/
│ ├─ routes/
│ ├─ schemas/
│ ├─ services/
│ └─ types/
├─ shared/ # reserved for future shared contracts
├─ requirement.txt
└─ package.json
- Install dependencies:
npm install- Copy env templates:
cp client/.env.example client/.env
cp server/.env.example server/.env- Choose a data mode in
server/.env:
DATA_PROVIDER=memoryfor local demo dataDATA_PROVIDER=firestorefor Firebase Firestore
- If using Firestore, configure:
FIREBASE_PROJECT_IDFIREBASE_CLIENT_EMAILFIREBASE_PRIVATE_KEY
- If using the AI assistant, configure:
GEMINI_API_KEYorGOOGLE_API_KEY- optionally
GEMINI_MODEL
- Start the backend:
npm run dev:server- Start the frontend in another terminal:
npm run dev:clientnpm run dev:servernpm run dev:clientnpm run buildnpm run build:servernpm run build:client
GET /api/expensesPOST /api/expensesPUT /api/expenses/:idDELETE /api/expenses/:id
GET /api/categoriesPOST /api/categoriesPUT /api/categories/:idDELETE /api/categories/:id
GET /api/budgets?month=YYYY-MMPOST /api/budgets
POST /api/chat
Example:
{
"message": "I spent 450 on Zomato using HDFC card"
}- The server defaults to a memory adapter so the UI works immediately during local development.
- Switching
DATA_PROVIDER=firestoreenables the production Firestore path without changing the client. - The client sends
x-user-idon each request. Default isdemo-user. - In production, the API now expects Firebase bearer tokens by default and no longer trusts the dev fallback identity path.
npm --workspace client run buildnpm --workspace server run build- API smoke-tested locally against
GET /api/health,GET /api/categories,GET /api/expenses,GET /api/budgets, andPOST /api/chat