# Production image. Development uses .devcontainer/Dockerfile instead. FROM python:3.13-slim-bookworm AS builder COPY --from=ghcr.io/astral-sh/uv:0.9.7 /uv /usr/local/bin/uv ENV UV_COMPILE_BYTECODE=1 \ UV_LINK_MODE=copy \ UV_PROJECT_ENVIRONMENT=/opt/venv WORKDIR /build # Dependencies resolve from the lockfile alone, so this layer stays cached # across source-only changes. COPY pyproject.toml uv.lock ./ RUN uv sync --frozen --no-dev --no-install-project COPY src/ ./src/ COPY README.md ./ RUN uv sync --frozen --no-dev FROM python:3.13-slim-bookworm AS runtime RUN groupadd --system --gid 1001 app \ && useradd --system --uid 1001 --gid app --create-home app ENV PATH=/opt/venv/bin:$PATH \ PYTHONUNBUFFERED=1 \ PYTHONDONTWRITEBYTECODE=1 COPY --from=builder --chown=app:app /opt/venv /opt/venv WORKDIR /app COPY --chown=app:app alembic.ini ./ COPY --chown=app:app migrations/ ./migrations/ USER app EXPOSE 8000 # Migrations are deliberately NOT run here: with more than one replica they # would race. Run `alembic upgrade head` as a separate deploy step. CMD ["gunicorn", "v2x_server.main:app", \ "--worker-class", "uvicorn.workers.UvicornWorker", \ "--workers", "4", \ "--bind", "0.0.0.0:8000", \ "--access-logfile", "-", \ "--timeout", "60"]