# Offline-Build-Protokoll — Build ohne Netzzugang (Issue #219) Nachweis für die in ADR 0024 §4 geforderte, ausdrücklich getroffene Entscheidung zur Reproduzierbarkeit ohne Netz. Belegstufe: **live verifiziert** — zweifach aus sauberem Checkout reproduziert. - **Datum:** 2026-07-31 - **Toolchain (gepinnt):** Container `node:22.15.1-alpine` (identisch zum Basis-Image der Deploy-Images, Node-Pin #236), pnpm `11.9.0` (`packageManager`-Feld in `package.json`, via corepack aktiviert). - **Netzisolation:** `docker run --network none` — der Build-Container hat keinerlei Egress; jede Netzabhängigkeit schlägt hart fehl. ## Entscheidung (ADR 0024 §4) **Beides, mit klarer Rollenverteilung:** 1. **Ausgelieferte Instanzen laufen aus Prebuilt-Images** (Release-Build der CI, digest-gepinnt, gespiegelt nach `95-mirror-protokoll.md`) — der Kunde baut für den Betrieb nichts selbst. 2. **Zusätzlich ist der Workspace-Build ohne Netz verifiziert** — die Behörde KANN lokal patchen (Quelloffenheit als Prüfvorteil), ohne dass dafür Internetzugang nötig wäre. ## Offline-Kit Einmalig auf einem Rechner **mit** Netz erzeugt: | Bestandteil | Erzeugung | Inhalt | | ------------------------------------ | ------------------------------------------------------ | ------------------------------------------------------------------- | | pnpm-Store (~870 MB) | `pnpm install --frozen-lockfile` mit `store-dir`-Mount | alle Pakete exakt nach `pnpm-lock.yaml` | | `~/.cache` des Build-Users (~460 MB) | fällt beim selben Install an | u. a. die Prisma-Engines, die das prisma-Postinstall sonst nachlädt | | optional: `drawio-30.3.6.tar.gz` | einmalig von der gepinnten GitHub-Release-URL | nur für das installierbare drawio-Plugin-ZIP nötig (s. u.) | ## Prozedur (offline) ```sh # sauberer Checkout + Offline-Kit gemountet, KEIN Netz: docker run --rm --network none -e CI=1 \ -v :/work -v :/pnpm-store -v :/root/.cache \ -w /work node:22.15.1-alpine sh -c ' corepack enable && corepack prepare pnpm@11.9.0 --activate pnpm config set store-dir /pnpm-store pnpm install --offline --frozen-lockfile pnpm build' ``` ## Ergebnis | Lauf | Checkout | `pnpm install --offline` | `pnpm build` | Artefakte geprüft | | ---- | -------------------- | ------------------------ | ------------ | --------------------------------------------------- | | 1 | frisch (git archive) | OK (11,8 s) | Exit 0 | `apps/api/dist/main.js`, `apps/web/dist/index.html` | | 2 | frisch (git archive) | OK | Exit 0 | identisch vorhanden | ## Befund und bewusste Grenze - **Einzige Netzabhängigkeit im Build:** das drawio-Plugin holt beim ersten Bau seines **installierbaren ZIPs** das gepinnte draw.io-Release-Tarball (v30.3.6) von GitHub nach `vendor/`. Ohne Netz und ohne `CI=1` schlägt genau dieser Schritt fehl (beobachtet, Lauf 0 dieses Protokolls). - **Einordnung:** Die Deploy-Images enthalten keine Plugin-ZIPs — Plugins werden zur Laufzeit über die Dropzone installiert. Der auslieferungsrelevante Build ist damit vollständig offline; `CI=1` (der auch in der CI gilt) überspringt den Vendor-Fetch und baut das Controller-Bundle. Wer das drawio-ZIP offline bauen will, legt das Tarball aus dem Offline-Kit vorab als `packages/plugins/drawio/vendor/drawio-30.3.6.tar.gz` ab — der Build lädt nur, was nicht schon dort liegt. - Prisma-Engines kommen offline aus `~/.cache` — der Cache gehört deshalb fest zum Kit (ohne ihn schlägt das prisma-Postinstall fehl). ## Konsequenz „kein lokales Patchen"? Entfällt — mit dem Offline-Kit ist lokales Patchen möglich. Wer es organisatorisch ausschließen will, betreibt nur die Prebuilt-Images; beides ist dokumentiert und die Wahl liegt beim Betreiber (Betriebshandbuch §1).