E-commerce review intelligence platform: ingest product reviews, run three ML pipelines in parallel (sentiment, fake detection, aspect scores), and visualize insights in a Vue dashboard.
Browser (Vue 3 SPA — JavaScript)
│ REST + JWT
▼
FastAPI (backend/app)
├── /auth → register, login, refresh, me
├── /products → CRUD (owner-scoped)
├── /reviews → ingest, list, bulk CSV
└── /analyze → sentiment trend, fake alerts, aspects, rerun
│
├── SQL (SQLite dev / PostgreSQL prod)
│ users, products, reviews, analysis_results
└── MongoDB
raw_reviews, ingest_logs
│
▼
ML layer (backend/ml)
├── sentiment.py → HuggingFace DistilBERT
├── fake_detector.py → XGBoost + TF-IDF
└── aspect/ → PyTorch biLSTM (price, quality, shipping, service)
Review flow: POST /reviews → SQL + Mongo → background run_full_pipeline() → sentiment → fake → aspects → analysis_results row → status: complete.
- Python 3.11+ (3.13 works with pinned
pymongoinrequirements.txt) - MongoDB 7 (local or Docker)
- Node.js 20+
- Optional: uv for faster installs
cd backend
python -m venv .venv && source .venv/bin/activate
pip install -r requirements.txt
pip install -r ml/requirements-ml.txt
cp .env.example .env
# Set SECRET_KEY and DATABASE_URL at minimum
alembic upgrade head
docker run -d --name reviewsense-mongo -p 27017:27017 mongo:7
uvicorn app.main:app --reload --port 8000- Swagger UI: http://localhost:8000/docs
- Health: http://localhost:8000/health
cd frontend
npm install
cp .env.example .env.local
# VITE_API_URL=http://localhost:8000
npm run devOpen http://localhost:5173 — register, then use Products and Analytics.
Stack: Vue 3, Vite, Pinia, Vue Router, Bootstrap 5, ApexCharts, Axios — JavaScript only (no TypeScript).
Artifacts are gitignored under backend/ml/models/. Train locally:
cd backend
python -m ml.train_fake_detector --generate-synthetic
python -m ml.aspect.train --generate-synthetic --epochs 10
# DistilBERT downloads automatically on first API startup (~250MB)| File | Model |
|---|---|
ml/models/xgb_model.pkl |
Fake detector |
ml/models/tfidf_vectorizer.pkl |
Feature pipeline |
ml/models/aspect_model.pt |
Aspect biLSTM weights |
ml/models/aspect_vocab.json |
Aspect tokenizer vocab |
| Route | Description |
|---|---|
/login, /register |
JWT authentication |
/dashboard |
Protected home |
/products |
Product card grid, search, pagination, add modal |
/products/:id |
Product detail — reviews tab, single review form, CSV bulk upload |
/analytics |
Sentiment trend chart |
Product detail — Reviews tab:
- Add review modal (
ReviewForm.vue) — author, 1–5 stars, body (min 20 chars) - Bulk CSV upload (
BulkUpload.vue) — drag-drop, 10MB limit, progress bar, polls job status - Review cards show sentiment and fake-review badges when analysis is complete
| Method | Path | Description |
|---|---|---|
| POST | /register |
Create account → JWT pair |
| POST | /login |
Login → JWT pair |
| POST | /refresh |
Bearer refresh token → new pair |
| GET | /me |
Current user profile |
| Method | Path | Description |
|---|---|---|
| GET | / |
List own products (page, limit, search) |
| POST | / |
Create product |
| GET | /{id} |
Product detail |
| PUT | /{id} |
Partial update |
| DELETE | /{id} |
Delete → 204 |
| Method | Path | Description |
|---|---|---|
| POST | / |
Submit single review → triggers ML pipeline |
| POST | /bulk-upload |
CSV upload (product_id + file) |
| GET | / |
List with filters (product_id, sentiment, dates) |
| GET | /{id} |
Review + analysis_result when complete |
| GET | /bulk-jobs/{job_id} |
CSV job status (MongoDB) |
| Method | Path | Description |
|---|---|---|
| GET | /sentiment-trend?product_id= |
Daily sentiment aggregates |
| GET | /fake-alerts |
Paginated fake review alerts |
| POST | /aspects |
Score arbitrary text |
| GET | /aspect-summary/{product_id} |
Avg aspect scores for a product |
| POST | /rerun/{review_id} |
Re-queue ML pipeline → 202 |
| Method | Path | Description |
|---|---|---|
| GET | /health |
API + Mongo status |
| Variable | Required | Default / notes |
|---|---|---|
SECRET_KEY |
Yes | JWT signing |
DATABASE_URL |
Yes | sqlite+aiosqlite:///./reviewsense.db |
MONGODB_URL |
No | mongodb://localhost:27017 |
MONGODB_DB_NAME |
No | reviewsense |
HF_MODEL_ID |
No | DistilBERT SST-2 model id |
ALLOWED_ORIGINS |
No | CORS origins (comma-separated) |
VITE_API_URL |
Frontend | http://localhost:8000 |
See backend/.env.example and frontend/.env.example.
ReviewSenseAI/
├── README.md
├── backend/
│ ├── app/ # FastAPI routers, services, models
│ ├── ml/ # ML pipelines + training scripts
│ ├── alembic/
│ └── requirements.txt
└── frontend/ # Vue 3 SPA (JavaScript)
├── src/
│ ├── api/axios.js
│ ├── stores/ # auth.js, products.js
│ ├── views/ # Login, Products, Analytics, …
│ └── components/ # ReviewForm, BulkUpload, SentimentChart, …
└── vite.config.js
pip install -r requirements.txt --force-reinstallpymongo>=4.6,<4.10 is pinned for Motor 3.7.x compatibility.
- Train fake-detector and aspect models (see ML setup above)
- First API startup downloads DistilBERT (needs network)
- Check uvicorn logs for ML errors
- Confirm backend is on port 8000
- Set
VITE_API_URLinfrontend/.env.local - Ensure
ALLOWED_ORIGINSincludeshttp://localhost:5173
Portfolio project: FastAPI · SQLAlchemy · MongoDB · Scikit-learn · XGBoost · HuggingFace · PyTorch · Vue 3 · Bootstrap · ApexCharts.