# ============================================================
# Dockerfile — Full application (frontend + backend)
# ============================================================
# Multi-stage build:
#   1. chef     – install cargo-chef for dependency caching
#   2. planner  – generate recipe.json from the workspace
#   3. backend  – build the backend binary (release)
#   4. frontend – build the frontend WASM bundle with Trunk
#   5. runtime  – minimal image: backend binary + static frontend + nginx
# ============================================================

# --------------- Stage 1: Chef base ---------------
FROM rust:1-bookworm AS chef
RUN cargo install cargo-chef
WORKDIR /app

# --------------- Stage 2: Planner ---------------
FROM chef AS planner
COPY Cargo.toml Cargo.lock ./
COPY src/ src/
COPY backend/ backend/
COPY frontend/ frontend/
RUN cargo chef prepare --recipe-path recipe.json

# --------------- Stage 3: Backend builder ---------------
FROM chef AS backend-builder

COPY --from=planner /app/recipe.json recipe.json
RUN cargo chef cook --release --recipe-path recipe.json -p backend

COPY Cargo.toml Cargo.lock ./
COPY src/ src/
COPY backend/ backend/
COPY frontend/ frontend/
RUN cargo build --release -p backend

# --------------- Stage 4: Frontend builder ---------------
FROM chef AS frontend-builder

# Add the WASM target
RUN rustup target add wasm32-unknown-unknown

# Install Trunk (the WASM bundler used by the frontend) and sass (for SCSS)
RUN cargo install trunk

# Cache frontend dependencies
COPY --from=planner /app/recipe.json recipe.json
RUN cargo chef cook --release --target wasm32-unknown-unknown --recipe-path recipe.json -p frontend

# Copy full workspace source for the build
COPY Cargo.toml Cargo.lock ./
COPY src/ src/
COPY backend/ backend/
COPY frontend/ frontend/

# Build the frontend WASM bundle
# Trunk outputs to frontend/dist by default
WORKDIR /app/frontend
RUN trunk build --release

# --------------- Stage 5: Runtime ---------------
FROM debian:bookworm-slim AS runtime

# Install runtime dependencies:
#   - ca-certificates & libssl3: TLS for PostgreSQL connections
#   - nginx: serves the frontend static files and reverse-proxies /api to the backend
RUN apt-get update && \
    apt-get install -y --no-install-recommends ca-certificates libssl3 nginx && \
    rm -rf /var/lib/apt/lists/*

WORKDIR /app

# Copy the compiled backend binary
COPY --from=backend-builder /app/target/release/backend /app/backend

# Copy migrations
COPY backend/migrations/ /app/migrations/

# Copy the frontend static build output
COPY --from=frontend-builder /app/frontend/dist /var/www/html

# Nginx configuration: serve frontend + reverse-proxy /api to the backend
RUN cat > /etc/nginx/sites-available/default <<'EOF'
server {
    listen 80;
    server_name _;

    root /var/www/html;
    index index.html;

    # Serve static frontend files, fall back to index.html for client-side routing
    location / {
        try_files $uri $uri/ /index.html;
    }

    # Reverse-proxy API requests to the Axum backend
    location /api/ {
        proxy_pass http://127.0.0.1:8001;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}
EOF

# Startup script: launch backend in the background, then nginx in the foreground
RUN cat > /app/start.sh <<'SCRIPT'
#!/bin/bash
set -e

# Start the backend API server in the background
/app/backend &

# Start nginx in the foreground (keeps the container alive)
nginx -g 'daemon off;'
SCRIPT
RUN chmod +x /app/start.sh

EXPOSE 80

# Environment variables should be provided at runtime:
#   DATABASE_URL    – PostgreSQL connection string
#   TOKEN_SECRET    – JWT signing key
#   ORIGIN          – Allowed CORS origin (should be the public URL of this container)

CMD ["/app/start.sh"]
