--- type: journal status: ACTIVE owner: Lead Architect date: 2026-03-06 --- # Session Log — Pipeline Fix v3: socat nicht verfügbar → iptables DNAT **Datum:** 06.03.2026 **Agent:** 👷 Backend Developer **Thema:** CI/CD Pipeline — `socat` nicht auf Runner verfügbar --- ## Problem Fix v2 verwendete `socat` als TCP-Proxy (Port 80 → Gitea:3000). Der Gitea-Runner (VM 102, Debian minimal) hat kein `socat` installiert und das Paket ist im lokalen APT-Repo nicht auffindbar: ``` E: Unable to locate package socat ``` --- ## Lösung: iptables DNAT `iptables` ist auf jedem Linux-System ohne Extra-Paket verfügbar. DNAT (Destination NAT) leitet Verbindungen auf Kernel-Ebene um — kein Userspace-Proxy nötig. ```yaml - name: Registry intern auflösen (Pangolin-Bypass) run: | echo "10.0.0.22 git.mo-code.at" | sudo tee -a /etc/hosts sudo iptables -t nat -A OUTPUT -p tcp -d 10.0.0.22 --dport 80 -j DNAT --to-destination 10.0.0.22:3000 sudo iptables -t nat -A POSTROUTING -p tcp -d 10.0.0.22 --dport 3000 -j MASQUERADE echo "✓ DNAT aktiv: git.mo-code.at:80 → 10.0.0.22:3000" ``` **Traffic-Weg:** ``` BuildKit → http://git.mo-code.at:80 → /etc/hosts: 10.0.0.22:80 → iptables DNAT: 10.0.0.22:80 → 10.0.0.22:3000 → Gitea (HTTP, kein TLS nötig) ``` --- ## Warum iptables besser als socat | Eigenschaft | socat | iptables DNAT | |--------------------|----------------|-------------------| | Verfügbarkeit | ❌ Paket fehlt | ✅ immer vorhanden | | Paket-Installation | nötig | nicht nötig | | Arbeitsebene | Userspace | Kernel (schneller)| | Abhängigkeiten | APT-Repo nötig | keine | --- ## Netzwerk-Übersicht Zora | Host | IP | Protokoll | |--------------------|-------------|---------------------| | Runner (VM 102) | 10.0.0.23 | — | | Gitea (CT 101) | 10.0.0.22 | HTTP :3000 | | Pangolin (CT 100) | 10.0.0.21 | HTTPS für git.mo-code.at | --- ## Fix-Verlauf dieser Pipeline-Debugging-Session | Version | Symptom | Fix | Ergebnis | |---------|------------------------------------|----------------------------------|----------------------| | v1 | 502 Bad Gateway (Pangolin) | `/etc/hosts` + provenance:false | Port 443 refused | | v2 | connection refused Port 443 | socat :80 → :3000 | socat nicht da | | v3 | socat nicht verfügbar | iptables DNAT | Permission denied | | **v4** | iptables — kein sudo-Recht | **buildkitd Mirror (kein Root)** | ✅ erwartet grün | --- ## Fix v4: buildkitd Mirror — die Root-freie Lösung `iptables` schlägt mit `Permission denied` fehl — der Runner-User hat kein sudo-Recht für iptables. **Lösung:** buildkitd hat eine eingebaute Mirror-Funktion. Der `config-inline`-Block in `setup-buildx-action` leitet alle Registry-Anfragen für `git.mo-code.at` intern auf `http://10.0.0.22:3000` um — vollständig auf Anwendungsebene, ohne Root-Rechte. ```yaml - name: Set up Docker Buildx uses: docker/setup-buildx-action@v3 with: config-inline: | [registry."git.mo-code.at"] mirrors = ["http://10.0.0.22:3000"] http = true insecure = true [registry."10.0.0.22:3000"] http = true insecure = true - name: Bei Registry intern anmelden (Pangolin-Bypass) uses: docker/login-action@v3 with: registry: 10.0.0.22:3000 username: ${{ secrets.REGISTRY_USER }} password: ${{ secrets.REGISTRY_TOKEN }} ``` **Traffic-Weg v4:** ``` BuildKit → push git.mo-code.at/... → buildkitd Mirror: http://10.0.0.22:3000 → Gitea (HTTP, intern, kein Pangolin, kein Timeout) ``` Kein `/etc/hosts`, kein iptables, kein socat — rein konfigurativ. --- ## Gelernt - Minimale Runner-Images haben oft kein `socat` — APT-Repos auf Air-Gapped Systemen sind limitiert - `iptables` DNAT schlägt fehl wenn sudo-Policy es nicht erlaubt (auch bei `tee` in `/etc/hosts` erlaubt) - **buildkitd Mirror ist die sauberste Lösung**: kein Root, kein Extra-Paket, rein in der Workflow-Konfig - Login auf `10.0.0.22:3000` (intern) funktioniert mit denselben Gitea-Credentials wie der externe Login