A web app that lets users discover and add UNESCO World Heritage Sites related to fandoms
(like Star Wars, Anime, K-Pop, etc.).
Built with FastAPI (Python) and Next.js (React/TypeScript).
FanHeritageApp/ ├─ api/ → FastAPI backend (Python) └─ web/ → Next.js frontend (React/TypeScript)
- Python 3.11+
- Node.js 18+ (includes npm)
cd FanHeritageApp/api
python -m venv .venv
source .venv/bin/activate # (Mac/Linux)
# .venv\Scripts\activate # (Windows)
pip install -r requirements.txt
cp .env.example .env
uvicorn app.main:app --reload
✅ The API runs on http://localhost:8000
Swagger Docs: http://localhost:8000/docs
2. Frontend Setup (Next.js)
cd FanHeritageApp/web
npm install
cp .env.local.example .env.local
Edit .env.local and make sure it contains:
NEXT_PUBLIC_API_URL=http://localhost:8000
3. Run Backend + Frontend Together
From inside the web folder:
npm run dev
This will:
Start the backend (FastAPI) on http://localhost:8000
Start the frontend (Next.js) on http://localhost:3000
Stop both servers with Ctrl + C
💻 How to Use
Open your browser and go to http://localhost:3000
You'll see the list of UNESCO sites (empty at first)
Click "Add Site" in the header
Fill in the site's details and submit
The new site will appear on the homepage!
---
## 🔐 Authentication
The app includes user authentication with JWT tokens:
### Features
- **User Registration** (`/register`) - Create an account with username, email, and password
- **User Login** (`/login`) - Sign in to get a JWT access token
- **Protected Routes** - Some endpoints require authentication
- **Token Management** - JWT tokens stored in localStorage, valid for 7 days
### API Endpoints
- `POST /api/auth/register` - Create new user account
- `POST /api/auth/login` - Login and receive access token
- `GET /api/auth/me` - Get current user info (requires authentication)
### Security
- Passwords are hashed using bcrypt
- JWT tokens signed with HS256 algorithm
- Email validation using pydantic EmailStr
- Minimum password length: 6 characters
### Important Notes
- The backend uses `bcrypt<5.0` due to compatibility with passlib
- Set `SECRET_KEY` environment variable in production
- Default SECRET_KEY is for development only