# Quick Start Guide

Get Flyer Crawler running in 5 minutes.

---

## Prerequisites Checklist

Before starting, verify you have:

- [ ] **Windows 10/11** with WSL 2 enabled
- [ ] **Podman Desktop** installed ([download](https://podman-desktop.io/))
- [ ] **Node.js 20+** installed
- [ ] **Git** for cloning the repository

**Verify Prerequisites**:

```bash
# Check Podman
podman --version
# Expected: podman version 4.x or higher

# Check Node.js
node --version
# Expected: v20.x or higher

# Check WSL
wsl --list --verbose
# Expected: Shows WSL 2 distro
```

---

## Quick Setup (5 Steps)

### Step 1: Start Containers (1 minute)

```bash
# Start PostgreSQL and Redis
podman start flyer-crawler-postgres flyer-crawler-redis

# If containers don't exist yet, create them:
podman run -d --name flyer-crawler-postgres \
  -e POSTGRES_USER=postgres \
  -e POSTGRES_PASSWORD=postgres \
  -e POSTGRES_DB=flyer_crawler_dev \
  -p 5432:5432 \
  docker.io/postgis/postgis:15-3.3

podman run -d --name flyer-crawler-redis \
  -p 6379:6379 \
  docker.io/library/redis:alpine
```

**Expected Output**:

```text
# Container IDs displayed, no errors
```

### Step 2: Initialize Database (2 minutes)

```bash
# Wait for PostgreSQL to be ready
podman exec flyer-crawler-postgres pg_isready -U postgres
# Expected: localhost:5432 - accepting connections

# Install extensions
podman exec flyer-crawler-postgres psql -U postgres -d flyer_crawler_dev \
  -c "CREATE EXTENSION IF NOT EXISTS postgis; CREATE EXTENSION IF NOT EXISTS pg_trgm; CREATE EXTENSION IF NOT EXISTS \"uuid-ossp\";"

# Apply schema
podman exec -i flyer-crawler-postgres psql -U postgres -d flyer_crawler_dev < sql/master_schema_rollup.sql
```

**Expected Output**:

```text
CREATE EXTENSION
CREATE EXTENSION
CREATE EXTENSION
CREATE TABLE
... (many tables created)
```

### Step 3: Configure Environment (1 minute)

Create `.env.local` in the project root:

```bash
# Database
DB_HOST=localhost
DB_USER=postgres
DB_PASSWORD=postgres
DB_NAME=flyer_crawler_dev
DB_PORT=5432

# Redis
REDIS_URL=redis://localhost:6379

# Application
NODE_ENV=development
PORT=3001
FRONTEND_URL=http://localhost:5173

# Secrets (generate your own - see command below)
JWT_SECRET=your-dev-jwt-secret-at-least-32-chars-long
SESSION_SECRET=your-dev-session-secret-at-least-32-chars-long

# AI Services (get your own keys)
GEMINI_API_KEY=your-google-gemini-api-key
GOOGLE_MAPS_API_KEY=your-google-maps-api-key
```

**Generate Secure Secrets**:

```bash
node -e "console.log(require('crypto').randomBytes(32).toString('hex'))"
```

### Step 4: Install and Run (1 minute)

```bash
# Install dependencies (first time only)
npm install

# Start development server
npm run dev
```

**Expected Output**:

```text
> flyer-crawler@x.x.x dev
> concurrently ...

[API] Server listening on port 3001
[Vite] VITE ready at http://localhost:5173
```

### Step 5: Verify Installation

| Check       | URL/Command                    | Expected Result                     |
| ----------- | ------------------------------ | ----------------------------------- |
| Frontend    | `http://localhost:5173`        | Flyer Crawler app loads             |
| Backend API | `http://localhost:3001/health` | `{ "status": "ok", ... }`           |
| Database    | `podman exec ... psql -c ...`  | `SELECT version()` returns Postgres |
| Containers  | `podman ps`                    | Shows postgres and redis running    |

---

## Full Dev Container (Recommended)

For a production-like environment with NGINX, Bugsink error tracking, and PM2 process management:

### Starting the Dev Container

```bash
# Start all services
podman-compose -f compose.dev.yml up -d

# View logs
podman-compose -f compose.dev.yml logs -f
```

### Access Points

| Service     | URL                      | Notes                        |
| ----------- | ------------------------ | ---------------------------- |
| Frontend    | `https://localhost`      | NGINX proxy to Vite          |
| Backend API | `http://localhost:3001`  | Express server               |
| Bugsink     | `https://localhost:8443` | Error tracking (admin/admin) |
| PostgreSQL  | `localhost:5432`         | Database                     |
| Redis       | `localhost:6379`         | Cache                        |

**SSL Certificate Setup (Recommended)**:

To eliminate browser security warnings, install the mkcert CA certificate:

```bash
# Windows: Double-click certs/mkcert-ca.crt and install to Trusted Root CAs
# See certs/README.md for detailed instructions per platform
```

### PM2 Commands

```bash
# View process status
podman exec -it flyer-crawler-dev pm2 status

# View logs (all processes)
podman exec -it flyer-crawler-dev pm2 logs

# Restart all processes
podman exec -it flyer-crawler-dev pm2 restart all

# Restart specific process
podman exec -it flyer-crawler-dev pm2 restart flyer-crawler-api-dev
```

### Dev Container Processes

| Process                    | Description              | Port |
| -------------------------- | ------------------------ | ---- |
| `flyer-crawler-api-dev`    | API server (tsx watch)   | 3001 |
| `flyer-crawler-worker-dev` | Background job worker    | -    |
| `flyer-crawler-vite-dev`   | Vite frontend dev server | 5173 |

---

## Verification Commands

Run these to confirm everything is working:

```bash
# Check containers are running
podman ps
# Expected: flyer-crawler-postgres and flyer-crawler-redis both running

# Test database connection
podman exec flyer-crawler-postgres psql -U postgres -d flyer_crawler_dev -c "SELECT version();"
# Expected: PostgreSQL 15.x with PostGIS

# Run tests (in dev container)
podman exec -it flyer-crawler-dev npm run test:unit
# Expected: All tests pass

# Run type check
podman exec -it flyer-crawler-dev npm run type-check
# Expected: No type errors
```

---

## Common Issues and Solutions

### "Unable to connect to Podman socket"

**Cause**: Podman machine not running

**Solution**:

```bash
podman machine start
```

### "Connection refused" to PostgreSQL

**Cause**: PostgreSQL still initializing

**Solution**:

```bash
# Wait for PostgreSQL to be ready
podman exec flyer-crawler-postgres pg_isready -U postgres
# Retry after "accepting connections" message
```

### Port 5432 or 6379 already in use

**Cause**: Another service using the port

**Solution**:

```bash
# Option 1: Stop conflicting service
# Option 2: Use different host port
podman run -d --name flyer-crawler-postgres -p 5433:5432 ...
# Then update DB_PORT=5433 in .env.local
```

### "JWT_SECRET must be at least 32 characters"

**Cause**: Secret too short in .env.local

**Solution**: Generate a longer secret:

```bash
node -e "console.log(require('crypto').randomBytes(32).toString('hex'))"
```

### Tests fail with "TZ environment variable" errors

**Cause**: Timezone setting interfering with Node.js async hooks

**Solution**: Tests must run in dev container (not Windows host):

```bash
# CORRECT - run in container
podman exec -it flyer-crawler-dev npm test

# INCORRECT - do not run on Windows host
npm test
```

---

## Next Steps

| Goal                    | Document                                              |
| ----------------------- | ----------------------------------------------------- |
| Understand the codebase | [Architecture Overview](../architecture/OVERVIEW.md)  |
| Configure environment   | [Environment Variables](ENVIRONMENT.md)               |
| Set up MCP tools        | [MCP Configuration](../tools/MCP-CONFIGURATION.md)    |
| Learn testing           | [Testing Guide](../development/TESTING.md)            |
| Understand DB schema    | [Database Documentation](../architecture/DATABASE.md) |
| Read ADRs               | [ADR Index](../adr/index.md)                          |
| Full installation guide | [Installation Guide](INSTALL.md)                      |

---

## Daily Development Workflow

```bash
# 1. Start containers
podman start flyer-crawler-postgres flyer-crawler-redis

# 2. Start dev server
npm run dev

# 3. Make changes and test
npm test

# 4. Type check before commit
npm run type-check

# 5. Commit changes
git commit
```

**For dev container users**:

```bash
# 1. Start dev container
podman-compose -f compose.dev.yml up -d

# 2. View logs
podman exec -it flyer-crawler-dev pm2 logs

# 3. Run tests
podman exec -it flyer-crawler-dev npm test

# 4. Stop when done
podman-compose -f compose.dev.yml down
```

---

Last updated: January 2026
