# ── Stage 1: Builder ────────────────────────────────────────────────────────── # # Uses the official Rust image on Debian Bookworm. # capnproto is installed here because build.rs invokes `capnp` at compile time. FROM rust:bookworm AS builder RUN apt-get update \ && apt-get install -y --no-install-recommends capnproto \ && rm -rf /var/lib/apt/lists/* WORKDIR /build # Copy manifests first so dependency layers are cached independently of source. COPY Cargo.toml Cargo.lock ./ COPY crates/quicprochat-core/Cargo.toml crates/quicprochat-core/Cargo.toml COPY crates/quicprochat-proto/Cargo.toml crates/quicprochat-proto/Cargo.toml COPY crates/quicprochat-server/Cargo.toml crates/quicprochat-server/Cargo.toml COPY crates/quicprochat-client/Cargo.toml crates/quicprochat-client/Cargo.toml COPY crates/quicprochat-p2p/Cargo.toml crates/quicprochat-p2p/Cargo.toml COPY crates/quicprochat-kt/Cargo.toml crates/quicprochat-kt/Cargo.toml COPY crates/quicprochat-plugin-api/Cargo.toml crates/quicprochat-plugin-api/Cargo.toml COPY crates/quicprochat-rpc/Cargo.toml crates/quicprochat-rpc/Cargo.toml COPY crates/quicprochat-sdk/Cargo.toml crates/quicprochat-sdk/Cargo.toml # Create dummy source files so `cargo build` can resolve the dependency graph # and cache the compiled dependencies before copying real source. RUN mkdir -p \ crates/quicprochat-core/src \ crates/quicprochat-proto/src \ crates/quicprochat-server/src \ crates/quicprochat-client/src \ crates/quicprochat-p2p/src \ crates/quicprochat-kt/src \ crates/quicprochat-plugin-api/src \ crates/quicprochat-rpc/src \ crates/quicprochat-sdk/src \ && echo 'fn main() {}' > crates/quicprochat-server/src/main.rs \ && echo 'fn main() {}' > crates/quicprochat-client/src/main.rs \ && touch crates/quicprochat-core/src/lib.rs \ && touch crates/quicprochat-proto/src/lib.rs \ && touch crates/quicprochat-p2p/src/lib.rs \ && touch crates/quicprochat-kt/src/lib.rs \ && touch crates/quicprochat-plugin-api/src/lib.rs \ && touch crates/quicprochat-rpc/src/lib.rs \ && touch crates/quicprochat-sdk/src/lib.rs # Schemas must exist before the proto crate's build.rs runs. COPY schemas/ schemas/ # Build dependencies only (source stubs mean this layer is cache-friendly). RUN cargo build --release --bin qpc-server 2>/dev/null || true # Copy real source and build for real. COPY crates/ crates/ # Touch source to force re-compilation after copying real crates. RUN touch \ crates/quicprochat-core/src/lib.rs \ crates/quicprochat-proto/src/lib.rs \ crates/quicprochat-p2p/src/lib.rs \ crates/quicprochat-kt/src/lib.rs \ crates/quicprochat-plugin-api/src/lib.rs \ crates/quicprochat-rpc/src/lib.rs \ crates/quicprochat-sdk/src/lib.rs \ crates/quicprochat-server/src/main.rs \ crates/quicprochat-client/src/main.rs RUN cargo build --release --bin qpc-server # ── Stage 2: Runtime ────────────────────────────────────────────────────────── # # Minimal Debian Bookworm image — no Rust toolchain, no capnp compiler. FROM debian:bookworm-slim AS runtime # ca-certificates is included so future HTTPS calls (e.g. from M6 key sync) # work without further changes to this stage. RUN apt-get update \ && apt-get install -y --no-install-recommends ca-certificates \ && rm -rf /var/lib/apt/lists/* COPY --from=builder /build/target/release/qpc-server /usr/local/bin/qpc-server # Create a dedicated non-root user with a writable data directory. RUN groupadd --system qpc \ && useradd --system --gid qpc --no-create-home --shell /usr/sbin/nologin qpc \ && mkdir -p /var/lib/quicprochat \ && chown qpc:qpc /var/lib/quicprochat EXPOSE 7000 # Persistent data volume: TLS certs, SQLCipher DB, delivery queues, KT log. # Mount a named volume or host path here for data persistence across restarts: # docker run -v qpc-data:/var/lib/quicprochat ... VOLUME ["/var/lib/quicprochat"] ENV RUST_LOG=info \ QPC_LISTEN=0.0.0.0:7000 \ QPC_DATA_DIR=/var/lib/quicprochat \ QPC_TLS_CERT=/var/lib/quicprochat/server-cert.der \ QPC_TLS_KEY=/var/lib/quicprochat/server-key.der \ QPC_PRODUCTION=true HEALTHCHECK --interval=30s --timeout=5s --retries=3 \ CMD test -f /var/lib/quicprochat/server-cert.der || exit 1 USER qpc CMD ["qpc-server"]