An AI-powered resume analysis and improvement tool built with React, Node.js, and the Google Gemini API.
- 📤 Upload & Parse — Drag-and-drop your resume (PDF or DOCX), parsed entirely in memory with no disk writes
- 🤖 AI Analysis — Gemini 2.5 Flash scores your resume on ATS compatibility, readability, and keyword density
- 📊 Visual Dashboard — Animated score ring, keyword match bars, strengths, weaknesses, and actionable suggestions
- ✍️ AI Resume Rewrite — One-click to generate an improved version of your resume with all suggestions applied
- 🖊️ Edit Before Download — Review and edit the AI-rewritten resume in a modal before saving
- 📥 PDF Export — Download the final improved resume as a clean, multi-page PDF via
jspdf
ResumeAnalyser/
├── backend/ # Node.js + Express API
│ ├── server.js # Main server — routes, file parsing, AI calls
│ ├── package.json
│ ├── .env # API keys (never commit this)
│ └── .gitignore
│
└── frontend/ # React + Vite SPA
├── public/
├── src/
│ ├── pages/
│ │ ├── Landing.jsx # Home page with hero and feature highlights
│ │ ├── Upload.jsx # Drag-and-drop upload + live PDF preview
│ │ └── Dashboard.jsx # Analysis results, score ring, edit/download
│ ├── components/
│ │ ├── Navbar.jsx # Responsive navigation bar
│ │ └── Footer.jsx # Site footer
│ ├── App.jsx # React Router setup (/, /upload, /dashboard)
│ ├── main.jsx # React entry point
│ └── index.css # Global design tokens + Tailwind base
├── .env # VITE_API_BASE_URL (never commit this)
├── vite.config.js
└── package.json
User uploads resume (PDF/DOCX)
│
▼
[Frontend: Upload.jsx]
POST /api/upload (multipart/form-data)
│
▼
[Backend: server.js]
1. Multer → reads file into memory buffer (no disk write)
2. pdf-parse / mammoth → extracts raw text
3. Gemini 2.5 Flash → returns structured JSON analysis
4. Returns { sessionId, aiAnalysis } to frontend
│
▼
[Frontend: Dashboard.jsx]
Renders score, strengths/weaknesses, keyword bars
│
▼ (on "Edit" or "Download Improved")
POST /api/improve (sends sessionId)
│
▼
[Backend: server.js]
1. Looks up resume text from in-memory cache (keyed by sessionId)
2. Gemini 2.5 Flash → rewrites the resume
3. Returns plain text
│
▼
[Frontend] → user edits in modal → jsPDF generates downloadable PDF
| Layer | Technology |
|---|---|
| Frontend Framework | React 19 + Vite |
| Styling | Tailwind CSS v4 + Custom CSS tokens |
| Animations | Framer Motion |
| Icons | Lucide React + Google Material Symbols |
| PDF Export | jsPDF |
| Backend | Node.js + Express 5 |
| File Parsing | pdf-parse (PDF), mammoth (DOCX) |
| File Uploads | Multer (memory storage) |
| AI | Google Gemini 2.5 Flash via @google/genai |
- Node.js v18+
- A Google Gemini API key (free)
git clone https://github.com/your-username/ResumeAnalyser.git
cd ResumeAnalysercd backend
npm installCreate a .env file in the backend/ folder:
GEMINI_API_KEY=your_gemini_api_key_here
PORT=3000Start the backend server:
npm start
# Server running at http://localhost:3000cd ../frontend
npm installCreate a .env file in the frontend/ folder:
VITE_API_BASE_URL=http://localhost:3000Start the frontend dev server:
npm run dev
# App running at http://localhost:5173Backend → Render (Free Tier)
- Push your code to GitHub (ensure
.envis not committed) - Go to render.com → New Web Service
- Connect your GitHub repo and configure:
| Setting | Value |
|---|---|
| Root Directory | backend |
| Build Command | npm install |
| Start Command | npm start |
| Instance Type | Free |
- Add Environment Variables in the Render dashboard:
| Key | Value |
|---|---|
GEMINI_API_KEY |
your Gemini API key |
PORT |
3000 |
- After deployment, copy your service URL (e.g.,
https://resumeanalyser-api.onrender.com)
Frontend → Vercel (Free Tier)
- Go to vercel.com → New Project
- Connect your GitHub repo and configure:
| Setting | Value |
|---|---|
| Root Directory | frontend |
| Framework Preset | Vite (auto-detected) |
- Add Environment Variables in the Vercel dashboard:
| Key | Value |
|---|---|
VITE_API_BASE_URL |
your Render backend URL |
- Click Deploy ✅
💡 Note: Render's free tier spins down after 15 minutes of inactivity. The first request after idle may take ~30 seconds.
GEMINI_API_KEY= # Required — Google Gemini API key
PORT=3000 # Port the server listens onVITE_API_BASE_URL= # Required — Full URL of your backend (no trailing slash)
# Local: http://localhost:3000
# Production: https://your-app.onrender.com- Resume files are never written to disk — processed in-memory via Multer's
memoryStorage() - Extracted text is cached in-memory per session with a 30-minute auto-expiry
- API keys are loaded via
dotenvand must be set as environment variables on the hosting platform — never hard-coded - File type validation rejects anything other than
.pdf,.doc,.docx - 10 MB file size limit enforced by Multer
MIT