--- name: "db-openshift-deploy" displayName: "DB OpenShift Deploy" description: "Manuelles Deployment im DB-Konzern: Docker-Image bauen, ins Artifactory (jFrog/bahnhub) pushen und auf einem OpenShift-Cluster (DBCS) per oc deployen. Inklusive Secrets, Image-Pull-Secret und Troubleshooting." keywords: ["openshift", "oc cli", "dbcs", "artifactory", "bahnhub", "docker image", "kubernetes deployment", "image pull secret", "imagepullbackoff"] author: "einfachbahn-lab" --- # DB OpenShift Deploy ## Overview Diese Power bündelt das Wissen, um eine containerisierte Anwendung im DB-Konzern **manuell** auf einem OpenShift-Cluster (DB Container Services, DBCS) zu betreiben: Image mit Docker bauen, ins **Artifactory** (`bahnhub.tech.rz.db.de`) pushen und mit `oc apply` deployen. Ideal für Prototypen, Labs und kleine Services. Für den standardisierten, compliance-konformen Weg siehe die Power **DB pipeship Onboarding**. ## Onboarding ### Voraussetzungen - **DeBi-Account** (SSO für Git, Artifactory, OpenShift). Für GitLab ist zusätzlich eine Bestellung im Digitalshop nötig. - **Docker Desktop** (Image-Build) - **`oc` CLI** (OpenShift-Client; aus der Console: `?` → *Command Line Tools*) - Ein **Docker-Repo im Artifactory** (einmalig über Self-Service https://bass.tech.db.de/welcome beantragen) - **Artifactory-API-Key**: https://bahnhub.tech.rz.db.de → Profil → *Edit Profile* → API Key ### Wichtige Links - Artifactory Self-Service: https://bass.tech.db.de/welcome - jFrog Artifactory: https://bahnhub.tech.rz.db.de/ui/packages - GitLab: https://git.tech.rz.db.de/ - OpenShift Console (Beispiel): https://console-openshift-console.apps.dbcs-riga.comp.db.de/ ## Key Concepts | Begriff | Bedeutung | |---------|-----------| | Image | Unveränderliches Paket aus App + Abhängigkeiten + Laufzeit | | Registry | Image-Speicher — hier Artifactory `bahnhub.tech.rz.db.de` | | OpenShift | Enterprise-Kubernetes von Red Hat (= k8s + Console, `oc`, `Route`, strenge SCC) | | Deployment | Beschreibt den Pod (Image, Env, Ressourcen, Health-Checks) | | Service | Cluster-interne stabile Adresse | | Route | OpenShift-Objekt: HTTPS-Zugang von außen (TLS-Termination) | | PVC | Persistenter Speicher, überlebt Pod-Neustarts | ## Common Workflows ### 1. Image bauen + pushen **Immer `--platform linux/amd64`** (auch auf Apple Silicon), Base-Images aus dem Artifactory-Mirror (kein Docker-Hub-Direktzugriff im Cluster). ```bash docker login einfachbahnlab-docker-stage-local.bahnhub.tech.rz.db.de # User=DeBi, Pass=API-Key docker build --platform linux/amd64 \ -t einfachbahnlab-docker-stage-local.bahnhub.tech.rz.db.de/api-viewer:0.8.0 . docker push einfachbahnlab-docker-stage-local.bahnhub.tech.rz.db.de/api-viewer:0.8.0 ``` ### 2. Erst-Setup im Namespace ```bash # Am Cluster anmelden (öffnet SSO im Browser) oc login https://api.dbcs-riga.comp.db.de:6443 # Image-Pull-Secret (sonst ImagePullBackOff) oc create secret docker-registry artifactory-pull -n einfachbahn-dev \ --docker-server=einfachbahnlab-docker-stage-local.bahnhub.tech.rz.db.de \ --docker-username=DEIN_USER --docker-password=DEIN_API_KEY # App-Secret (vertrauliche Werte) oc create secret generic babedas-api-viewer -n einfachbahn-dev \ --from-literal=AUTH_USER=... --from-literal=AUTH_PASS=... ``` ### 3. Deployen Manifeste mit Platzhaltern ``, ``, `` ersetzen und anwenden (Reihenfolge: pvc → deployment → service → route): ```bash for m in k8s/pvc.yaml k8s/deployment.yaml k8s/service.yaml k8s/route.yaml; do sed -e "s||einfachbahn-dev|g" \ -e "s||einfachbahnlab-docker-stage-local.bahnhub.tech.rz.db.de|g" \ -e "s||0.8.0|g" "$m" | oc apply -f - done oc rollout status deployment/api-viewer -n einfachbahn-dev ``` ### 4. Betrieb / Diagnose ```bash oc get pods -n einfachbahn-dev -l app=api-viewer oc logs -f deployment/api-viewer -n einfachbahn-dev | grep -v "GET /" oc exec -it deployment/api-viewer -n einfachbahn-dev -- sh oc set env deployment/api-viewer -n einfachbahn-dev FETCH_ON_START=true oc delete pod -l app=api-viewer -n einfachbahn-dev # Neustart nach Secret-Änderung ``` ## OpenShift-Besonderheiten (wichtig) - **Non-root**: Container laufen mit zufälliger UID. Schreib-Verzeichnisse weltbeschreibbar machen (`chmod 777 /app/data`), unter `/app` statt `/`. - **`restricted` SCC**: `privileged: false`, `runAsNonRoot: true`. Kein Docker-in-Docker. - **Kein Internet**: Images nur aus Artifactory-Mirror (`docker-hub-remote.bahnhub.tech.rz.db.de`). - **`Route` statt `Ingress`** für externen HTTPS-Zugang. ## Troubleshooting ### Pod: `ImagePullBackOff` Image-Pull-Secret `artifactory-pull` fehlt/falsch, oder Image-Tag existiert nicht. Secret neu anlegen, Tag prüfen. ### Pod: `CreateContainerConfigError` App-Secret fehlt oder ein referenzierter Key existiert nicht. ### `exec format error` / sofortiger Crash Falsche Architektur — mit `--platform linux/amd64` neu bauen. ### `docker push` → `unauthorized` / `denied` Nicht eingeloggt (`docker login`) oder kein Push-Recht/Repo fehlt (Self-Service prüfen). ### 502 Bad Gateway Pod noch nicht `ready` — Logs prüfen, warten. ### Daten weg nach Redeploy PVC prüfen: `oc get pvc -n einfachbahn-dev` (sollte erhalten bleiben). ## Best Practices - Feste, semantische Tags (`0.8.0`), kein `latest` für Deployments → nachvollziehbare Rollbacks. - Health-Checks (`livenessProbe`/`readinessProbe` auf `/health`) im Deployment. - Keine Secrets im Image oder Git — immer als OpenShift-Secret. - PVC niemals beim Aufräumen mitlöschen, wenn Daten erhalten bleiben sollen. ## Weiterführend Vollständige Doku, Scripts (`build-and-push.sh`, `deploy.sh`, `create-secret.sh`) und k8s-Manifest-Templates im Repo `einfachbahn-lab/doku/deployment-doku` (`docs/01`–`docs/07`, `scripts/`, `k8s/`).