434de9aa3e9f50221f8fb883305d393cb23d522b
- Backend Dockerfile: multi-stage build with venv, gunicorn+uvicorn workers, entrypoint runs alembic then gunicorn - Frontend Dockerfile: multi-stage with npm ci, nginx:1.27-alpine runtime - nginx.conf: gzip compression, security headers (X-Frame-Options, X-Content-Type-Options, etc.), static asset caching, correct API proxy preserving /api/ prefix - docker-compose.yml: production config — db healthcheck, backend healthcheck, frontend depends_on backend healthy, no exposed backend port - docker-compose.override.yml: dev hot-reload — uvicorn --reload with source mount, npm run dev on port 5173 - Rate limiting: slowapi middleware on /auth/login (10/min) and /auth/register (5/min) - README.md: full documentation with architecture, quick start, API table, dev/prod instructions, tests - .env.example: all variables documented with comments - .gitignore: extended with *.pyc, *.cover, .ruff_cache, frontend/.vite, etc. Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Budget Tracker
A personal finance web application to track income, expenses, and budgets with analytics and CSV/PDF export.
Stack
| Layer | Technology |
|---|---|
| Backend | FastAPI 0.115, SQLAlchemy 2.0 async, Alembic |
| Database | PostgreSQL 16 |
| Frontend | React 18, TypeScript, Vite, Tailwind CSS, Radix UI |
| Charts | Recharts |
| Export | CSV (native), PDF (WeasyPrint) |
| Server | Gunicorn + Uvicorn workers, Nginx 1.27 |
Quick Start
# 1. Copy and configure environment
cp .env.example .env
# 2. Start all services (production mode)
docker compose up -d
# App is available at http://localhost
# API docs at http://localhost/api/v1/docs
The backend automatically runs
alembic upgrade headon startup.
Architecture
┌─────────────┐ ┌──────────────────┐ ┌──────────────┐
│ Browser │──80──▶│ Nginx (frontend) │──/api/▶│ FastAPI │
└─────────────┘ │ serves SPA dist │ │ (gunicorn) │
└──────────────────┘ └──────┬───────┘
│
┌──────▼───────┐
│ PostgreSQL │
└──────────────┘
- Frontend: React SPA served by Nginx. All
/api/*requests are proxied to the backend. - Backend: FastAPI with async SQLAlchemy. Exposes REST API under
/api/v1. - Database: PostgreSQL with Alembic migrations applied at container start.
API Endpoints
Interactive docs (Swagger UI): http://localhost/api/v1/docs
| Module | Prefix | Description |
|---|---|---|
| Auth | /api/v1/auth |
Register, login, refresh, logout |
| Transactions | /api/v1/transactions |
CRUD + pagination + filters |
| Categories | /api/v1/categories |
Income / expense categories |
| Budgets | /api/v1/budgets |
Monthly budgets + rollover |
| Dashboard | /api/v1/dashboard |
Monthly summary + charts data |
| History | /api/v1/history |
Year-over-year analytics |
| Export | /api/v1/export |
CSV and PDF export |
| Health | /health |
Liveness probe |
Development (hot-reload)
The docker-compose.override.yml is automatically merged in dev, enabling:
- Backend:
uvicorn --reloadwith source code mounted - Frontend:
npm run dev(Vite HMR) on port 5173
# Start dev environment
cp .env.example .env
docker compose up
# Backend API: http://localhost:8000
# Frontend dev server: http://localhost:5173
# API docs: http://localhost:8000/api/v1/docs
Production
# Use only the base compose file (no override)
docker compose -f docker-compose.yml up -d
# Generate a secure SECRET_KEY
python -c "import secrets; print(secrets.token_hex(32))"
# Set in .env:
# SECRET_KEY=<generated value>
# CORS_ORIGINS=["https://your-domain.com"]
Tests
# Backend tests
cd backend
pip install -r requirements.txt
pytest
# With coverage
pytest --cov=app --cov-report=term-missing
# Frontend type check
cd frontend
npm run build # tsc -b + vite build
Project Structure
budget-tracker/
├── backend/
│ ├── app/
│ │ ├── auth/ # JWT auth (register, login, refresh, logout)
│ │ ├── models/ # SQLAlchemy ORM models
│ │ ├── routers/ # FastAPI routers (transactions, budgets, …)
│ │ ├── schemas/ # Pydantic request/response schemas
│ │ ├── services/ # Business logic layer
│ │ ├── config.py # Settings (pydantic-settings)
│ │ ├── database.py # Async engine + session factory
│ │ └── main.py # App factory + middleware
│ ├── alembic/ # Database migrations
│ ├── tests/ # pytest test suite
│ ├── Dockerfile # Multi-stage build (venv → slim runtime)
│ └── entrypoint.sh # alembic upgrade head → gunicorn
└── frontend/
├── src/
│ ├── api/ # Axios client + API functions
│ ├── components/ # Shared UI components
│ ├── hooks/ # React Query hooks
│ ├── pages/ # Route-level page components
│ └── stores/ # Zustand auth store
├── Dockerfile # Multi-stage build (npm ci → nginx)
└── nginx.conf # Gzip, security headers, SPA fallback, API proxy
Description
Languages
TypeScript
40.2%
Python
35.6%
Shell
22%
Dockerfile
0.9%
JavaScript
0.6%
Other
0.7%