# ---- build stage ------------------------------------------------------------
# pin builder and runtime to the same Debian release — a floating `rust:1-slim`
# drifts to a newer glibc than the runtime image and the binary refuses to start
FROM rust:1-slim-trixie AS builder
WORKDIR /app
# the cortiq runtime CANNOT be auto-installed inside the container (no cargo in
# the runtime image), so it is compiled here and shipped alongside the gateway —
# local .cmf chat models and image/video generation work in Docker out of the box
RUN cargo install cortiq-cli --locked
# the admin SPA (web/) is embedded at compile time via rust-embed, so it must be present
COPY Cargo.toml Cargo.lock ./
COPY src ./src
COPY web ./web
RUN cargo build --release

# ---- runtime stage ----------------------------------------------------------
FROM debian:trixie-slim
# curl — model imports download ready .cmf files with it;
# libvulkan1 — optional GPU offload for cortiq (falls back to CPU without a GPU)
RUN apt-get update \
    && apt-get install -y --no-install-recommends ca-certificates curl libvulkan1 \
    && rm -rf /var/lib/apt/lists/* \
    && useradd -r -u 10001 cortiq \
    && mkdir -p /app/config /app/data/models
COPY --from=builder /app/target/release/cortiq-gateway /usr/local/bin/cortiq-gateway
COPY --from=builder /usr/local/cargo/bin/cortiq /usr/local/bin/cortiq
# ship the example as the default config so `docker run` works out of the box
COPY config/gateway.example.toml /app/config/gateway.toml
RUN chown -R 10001:10001 /app
WORKDIR /app
# all gateway state (downloaded models, stats, secrets) lives under /app/data —
# mount a volume there to keep it across container recreates
ENV CORTIQ_GATEWAY_HOME=/app/data
# runs as root so writes to bind-mounted host folders (Docker Desktop on
# Windows/macOS) don't fail with permission errors (curl exit code 23);
# add `--user 10001` to docker run to harden when not using host bind mounts
EXPOSE 9000
ENTRYPOINT ["cortiq-gateway"]
CMD ["--config", "/app/config/gateway.toml"]
