A beginner-friendly full stack web application for tracking personal expenses. Built with React, Node.js, Express, and MongoDB.
| Layer | Technology |
|---|---|
| Frontend | React, React Router, Axios, CSS |
| Backend | Node.js, Express.js |
| Database | MongoDB + Mongoose |
| Auth | JWT + bcrypt |
expense-tracker/
βββ backend/ # Express API server
β βββ controllers/ # Route handler logic
β βββ models/ # MongoDB schemas
β βββ routes/ # API route definitions
β βββ middleware/ # Auth middleware
β βββ server.js # Entry point
β βββ .env # Environment variables
β βββ package.json
βββ frontend/ # React app (Vite)
β βββ src/
β β βββ components/ # Navbar, ProtectedRoute
β β βββ pages/ # Login, Register, Dashboard, AddExpense, EditExpense
β β βββ App.jsx # Main app with routing
β β βββ main.jsx # React entry point
β β βββ index.css # All styles
β βββ index.html
β βββ vite.config.js
β βββ package.json
βββ .github/workflows/ci.yml # GitHub Actions CI
βββ .gitignore
βββ README.md
git clone https://github.com/your-username/expense-tracker.git
cd expense-tracker
cd backend
npm install
Create a .env file in the backend/ folder:
PORT=5000
MONGO_URI=mongodb+srv://<username>:<password>@cluster0.xxxxx.mongodb.net/expense-tracker
JWT_SECRET=your_super_secret_key_change_this
cd frontend
npm install
Start backend (from backend/ folder):
npm run dev
Start frontend (from frontend/ folder):
npm run dev
Open http://localhost:5173 in your browser.
| Method | Endpoint | Description | Auth Required |
|---|---|---|---|
| POST | /api/auth/register | Create new account | No |
| POST | /api/auth/login | Login to account | No |
| GET | /api/auth/user | Get current user | Yes |
| Method | Endpoint | Description |
|---|---|---|
| GET | /api/expenses | Get all expenses |
| GET | /api/expenses/:id | Get single expense |
| POST | /api/expenses | Create expense |
| PUT | /api/expenses/:id | Update expense |
| DELETE | /api/expenses/:id | Delete expense |
localStorage on the browserAuthorization: Bearer <token> headerlocalStorage(Add screenshots here after running the app)
backendnpm installnpm startfrontendnpm run builddistVITE_API_URL = your Render URL<username> and <password> in your .env file{ "name": "Test", "email": "test@test.com", "password": "123456" }{ "email": "test@test.com", "password": "123456" }token from the responseAuthorization: Bearer <token> and body { "title": "Lunch", "amount": 15, "category": "Food" }Authorization: Bearer <token>Three GitHub Actions workflows in .github/workflows/ run automatically:
| Workflow | Trigger | Action |
|---|---|---|
ci.yml |
Every push / PR to main |
Install + syntax-check backend, build frontend |
vercel-deploy.yml |
Push to main (frontend changes) |
Build & deploy frontend to Vercel (--prod) |
render-deploy.yml |
Push to main (backend changes) |
POST to the Render deploy hook |
Add these under repo β Settings β Secrets and variables β Actions:
| Secret | How to get it |
|---|---|
VERCEL_TOKEN |
vercel.com/account/tokens β Create Token |
VERCEL_ORG_ID |
Run npx vercel link in frontend/, then copy orgId from .vercel/project.json |
VERCEL_PROJECT_ID |
Same projectId from .vercel/project.json |
RENDER_DEPLOY_HOOK_URL |
Render β Service β Settings β Deploy Hooks β Create Hook (URL like https://api.render.com/deploy/srv-xxx?key=yyy) |
JWT_SECRET is auto-generated by render.yaml. Override it in the Render dashboard if you like.VITE_API_URL=https://expense-tracker-api-olhn.onrender.com (already configured on the project).β οΈ Data persistence: the backend stores data in
backend/data/*.json. Render free instances have an ephemeral filesystem, so data is lost whenever the service restarts or redeploys. For a persistent database, migrate the models to MongoDB Atlas (theMONGO_URIenv var) β see the README architecture diagram.
Q1: What is JWT and why is it used? A: JWT (JSON Web Token) is a compact, URL-safe token used for authentication. It contains encoded user information and is signed with a secret key. We use it so users donβt have to send their password on every request.
Q2: How does bcrypt work? A: bcrypt is a password hashing function. It adds a random βsaltβ to the password before hashing, making it resistant to rainbow table attacks. We store only the hashed version, never the plain text password.
Q3: What is middleware in Express?
A: Middleware are functions that execute during the request-response cycle. Our authMiddleware runs before protected route handlers to verify the JWT token.
Q4: What is the difference between SQL and NoSQL? A: SQL databases (like MySQL) use tables with fixed schemas. NoSQL databases (like MongoDB) use flexible documents. MongoDB is easier for beginners because you can store JSON-like data without predefined schemas.
Q5: How does React Router work?
A: React Router is a library that enables navigation between different components without page refresh. It uses Routes and Route components to map URLs to components.
Q6: What is CORS? A: CORS (Cross-Origin Resource Sharing) is a security mechanism that allows a web page from one domain to access resources on another domain. We enable it in Express so our React frontend can call the backend API.
Q7: Explain the flow when a user logs in.
A: User enters email/password β Frontend sends POST to /api/auth/login β Backend finds user, compares hashed password β If match, generates JWT token β Frontend stores token in localStorage β User is redirected to Dashboard.
Q8: What is the purpose of the .env file?
A: The .env file stores sensitive configuration like database URLs and secret keys. It keeps secrets out of the codebase and is listed in .gitignore so itβs never committed to GitHub.
βββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
β Browser (React) β
β ββββββββββββ ββββββββββββ βββββββββββββββββββββββββββββ β
β β Login β β Register β β Dashboard / Add / Edit β β
β β Page β β Page β β (Protected Routes) β β
β βββββββ¬βββββ βββββββ¬βββββ ββββββββββββ¬βββββββββββββββββ β
β β β β β
β ββββββββββββββββ΄βββββββββββββββββββ β
β β axios (HTTP requests) β
ββββββββββββββββββββββββββββΌβββββββββββββββββββββββββββββββββββ
β
ββββββββ΄ββββββββ
β CORS β
ββββββββ¬ββββββββ
β
ββββββββββββββββββββββββββββΌβββββββββββββββββββββββββββββββββββ
β Express Server β
β ββββββββββββ βββββββββ΄βββββββββ ββββββββββββββββββββ β
β β Auth β β Auth Middlewareβ β Expense Routes β β
β β Routes ββββΆβ (JWT Verify) ββββΆβ (CRUD) β β
β ββββββ¬ββββββ ββββββββββββββββββ ββββββββββ¬ββββββββββ β
β β β β
β ββββββ΄ββββββ ββββββββ΄ββββββββ β
β β Auth β β Expense β β
β βControllerβ β Controller β β
β ββββββ¬ββββββ ββββββββ¬ββββββββ β
β β β β
β ββββββ΄ββββββ ββββββββ΄ββββββββ β
β β User β β Expense β β
β β Model β β Model β β
β ββββββ¬ββββββ ββββββββ¬ββββββββ β
β β β β
βββββββββΌββββββββββββββββββββββββββββββββββββββββΌβββββββββββββ
β β
βββββββββββββββββ¬ββββββββββββββββββββββββ
β
ββββββββ΄βββββββ
β MongoDB β
β (Atlas) β
βββββββββββββββ
This project is for educational purposes as a college mini project.