Fehlerbehebung: Warum hängt mein Kubernetes-Pod im Status "Pending" oder "CrashLoopBackOff" fest?

Kubernetes-Pods, die in "Pending" oder "CrashLoopBackOff" feststecken, können Deployments stoppen. Dieser umfassende Leitfaden entschlüsselt diese häufigen Zustände und bietet praktische, schrittweise Fehlerbehebung. Lernen Sie, Probleme wie Ressourcenbeschränkungen, Image-Pull-Fehler, Anwendungsfehler und fehlerhafte Konfigurationen von Probes mithilfe von `kubectl`-Befehlen zu diagnostizieren. Stärken Sie sich mit umsetzbaren Erkenntnissen und Best Practices, um Pod-Probleme schnell zu lösen und eine robuste, zuverlässige Kubernetes-Umgebung aufrechtzuerhalten, um sicherzustellen, dass Ihre Anwendungen immer einsatzbereit sind.

30 Aufrufe

Fehlerbehebung: Warum hängt mein Kubernetes Pod im Status Pending oder CrashLoopBackOff?

Kubernetes hat die Art und Weise, wie wir containerisierte Anwendungen bereitstellen und verwalten, revolutioniert und bietet eine unübertroffene Skalierbarkeit und Ausfallsicherheit. Doch selbst in einer gut orchestrierten Umgebung können Pods manchmal auf Probleme stoßen, die sie daran hindern, den Status Running zu erreichen. Zwei der häufigsten und frustrierendsten Zustände für einen Pod sind Pending und CrashLoopBackOff. Das Verständnis, warum Ihre Pods in diesen Zuständen hängen bleiben und wie Sie sie effektiv diagnostizieren, ist entscheidend für die Aufrechterhaltung gesunder und zuverlässiger Anwendungen.

Dieser Artikel befasst sich mit den häufigsten Ursachen dafür, dass Pods in den Zuständen Pending oder CrashLoopBackOff stecken bleiben. Wir werden Probleme untersuchen, die von Ressourcenbeschränkungen und fehlgeschlagenen Image-Pulls bis hin zu anwendungsbezogenen Fehlern und falsch konfigurierten Probes reichen. Wichtiger noch, wir werden eine Schritt-für-Schritt-Anleitung mit praktischen kubectl-Befehlen bereitstellen, die Ihnen helfen, diese Bereitstellungsprobleme schnell zu diagnostizieren und zu lösen und sicherzustellen, dass Ihre Anwendungen reibungslos laufen.

Pod-Zustände verstehen: Pending vs. CrashLoopBackOff

Bevor wir mit der Fehlerbehebung beginnen, ist es wichtig zu verstehen, was diese beiden Zustände bedeuten.

Pod-Status: Pending

Ein Pod im Status Pending bedeutet, dass der Kubernetes-Scheduler den Pod akzeptiert hat, er aber noch nicht erfolgreich auf einem Knoten geplant wurde oder alle seine Container noch nicht erstellt/initialisiert wurden. Dies weist typischerweise auf ein Problem hin, das den Start des Pods auf einem Worker-Knoten verhindert.

Pod-Status: CrashLoopBackOff

Ein Pod im Status CrashLoopBackOff bedeutet, dass ein Container innerhalb des Pods wiederholt gestartet, abgestürzt und dann neu gestartet wird. Kubernetes implementiert eine exponentielle Verzögerung zwischen den Neustarts, um eine Überlastung des Knotens zu verhindern. Dieser Zustand weist fast immer auf ein Problem mit der Anwendung hin, die innerhalb des Containers selbst läuft, oder mit ihrer unmittelbaren Umgebung.

Fehlerbehebung bei Pods im Status Pending

Wenn ein Pod Pending ist, ist der erste Anlaufpunkt der Scheduler und der Knoten, auf den er zugegriffen werden soll. Hier sind die häufigsten Ursachen und Diagnose Schritte.

1. Unzureichende Ressourcen auf Knoten

Einer der häufigsten Gründe dafür, dass ein Pod Pending ist, ist, dass kein Knoten im Cluster über genügend verfügbare Ressourcen (CPU, Arbeitsspeicher) verfügt, um die requests des Pods zu erfüllen. Der Scheduler kann keinen geeigneten Knoten finden.

Diagnose Schritte:

  1. Pod beschreiben: Der Befehl kubectl describe pod ist hier Ihr bester Freund. Er zeigt oft Ereignisse an, die erklären, warum der Pod nicht geplant werden kann.
    bash kubectl describe pod <pod-name> -n <namespace>
    Suchen Sie nach Ereignissen wie "FailedScheduling" und Meldungen wie "0/3 nodes are available: 3 Insufficient cpu" oder "memory".

  2. Knotenressourcen prüfen: Sehen Sie sich die aktuelle Ressourcenauslastung und Kapazität Ihrer Knoten an.
    bash kubectl get nodes kubectl top nodes # (benötigt metrics-server)

Lösung:

  • Cluster-Kapazität erhöhen: Fügen Sie Ihrem Kubernetes-Cluster mehr Knoten hinzu.
  • Pod-Ressourcenanforderungen anpassen: Reduzieren Sie die requests für CPU und Arbeitsspeicher in der Manifestdatei Ihres Pods, wenn sie zu hoch eingestellt sind.
    yaml resources: requests: memory: "128Mi" cpu: "250m"
  • Andere Pods verdrängen: Manuelles Verdrängen von Pods mit geringerer Priorität von Knoten, um Ressourcen freizugeben (mit Vorsicht verwenden).

2. Fehler beim Image-Pull

Wenn Kubernetes den Pod auf einem Knoten planen kann, der Knoten aber das Container-Image nicht herunterladen kann, bleibt der Pod Pending.

Häufige Ursachen:

  • Falscher Image-Name/Tag: Tippfehler im Image-Namen oder Verwendung eines nicht vorhandenen Tags.
  • Authentifizierung bei privaten Registries: Fehlende oder falsche ImagePullSecrets für private Registries.
  • Netzwerkprobleme: Der Knoten kann die Image-Registry nicht erreichen.

Diagnose Schritte:

  1. Pod beschreiben: Auch hier ist kubectl describe pod entscheidend. Suchen Sie nach Ereignissen wie "Failed" oder "ErrImagePull" oder "ImagePullBackOff".
    bash kubectl describe pod <pod-name> -n <namespace>
    Beispielhafter Ausgabefehler: Failed to pull image "my-private-registry/my-app:v1.0": rpc error: code = Unknown desc = Error response from daemon: pull access denied for my-private-registry/my-app, repository does not exist or may require 'docker login'

  2. ImagePullSecrets prüfen: Überprüfen Sie, ob imagePullSecrets korrekt in Ihrem Pod oder ServiceAccount konfiguriert sind.
    bash kubectl get secret <your-image-pull-secret> -o yaml -n <namespace>

Lösung:

  • Korrekter Image-Name/Tag: Überprüfen Sie den Image-Namen und das Tag in Ihrer Deployment-Manifestdatei.
  • ImagePullSecrets konfigurieren: Stellen Sie sicher, dass Sie ein docker-registry-Secret erstellt und es mit Ihrem Pod oder ServiceAccount verknüpft haben.
    bash kubectl create secret docker-registry my-registry-secret \n --docker-server=your-registry.com \n --docker-username=your-username \n --docker-password=your-password \n --docker-email=your-email -n <namespace>
    Fügen Sie es dann Ihrer Pod-Spezifikation hinzu:
    ```yaml
    spec:
    imagePullSecrets:
    • name: my-registry-secret
      containers:
      ...
      ```
  • Netzwerkkonnektivität: Überprüfen Sie die Netzwerkkonnektivität vom Knoten zur Image-Registry.

3. Probleme mit Volumes

Wenn Ihr Pod einen PersistentVolumeClaim (PVC) benötigt und der entsprechende PersistentVolume (PV) nicht bereitgestellt oder gebunden werden kann, bleibt der Pod Pending.

Diagnose Schritte:

  1. Pod beschreiben: Suchen Sie nach ereignisbezogenen Volumen.
    bash kubectl describe pod <pod-name> -n <namespace>
    Ereignisse können Meldungen wie FailedAttachVolume, FailedMount oder ähnliches anzeigen.

  2. PVC- und PV-Status prüfen: Überprüfen Sie den Status des PVC und PV.
    bash kubectl get pvc <pvc-name> -n <namespace> kubectl get pv
    Suchen Sie nach PVCs, die in Pending hängen geblieben sind, oder nach PVs, die nicht gebunden sind.

Lösung:

  • StorageClass sicherstellen: Stellen Sie sicher, dass eine StorageClass definiert und verfügbar ist, insbesondere wenn Sie dynamische Bereitstellung verwenden.
  • PV-Verfügbarkeit prüfen: Wenn Sie statische Bereitstellung verwenden, stellen Sie sicher, dass der PV existiert und den PVC-Kriterien entspricht.
  • Zugriffsmodi überprüfen: Stellen Sie sicher, dass die Zugriffsmodi (z. B. ReadWriteOnce, ReadWriteMany) kompatibel sind.

Fehlerbehebung bei Pods im Status CrashLoopBackOff

Ein Status CrashLoopBackOff weist auf ein Problem auf Anwendungsebene hin. Der Container wurde erfolgreich gestartet, stürzte dann aber mit einem Fehler ab, was dazu führt, dass Kubernetes ihn wiederholt neu startet.

1. Anwendungsfehler

Die häufigste Ursache ist, dass die Anwendung selbst nicht startet oder kurz nach dem Start einen schwerwiegenden Fehler aufweist.

Häufige Ursachen:

  • Fehlende Abhängigkeiten/Konfiguration: Die Anwendung kann kritische Konfigurationsdateien, Umgebungsvariablen oder externe Dienste, auf die sie angewiesen ist, nicht finden.
  • Falscher Befehl/Argumente: Der in der Container-Spezifikation angegebene command oder args ist falsch oder führt zu einem sofortigen Beenden.
  • Fehler in der Anwendungslogik: Bugs im Anwendungscode, die dazu führen, dass sie beim Start abstürzt.

Diagnose Schritte:

  1. Pod-Protokolle anzeigen: Dies ist der wichtigste Schritt. Die Protokolle zeigen oft die genaue Fehlermeldung an, die den Absturz der Anwendung verursacht hat.
    bash kubectl logs <pod-name> -n <namespace>
    Wenn der Pod wiederholt abstürzt, zeigen die Protokolle möglicherweise die Ausgabe des letzten fehlgeschlagenen Versuchs. Um Protokolle einer früheren Instanz eines abstürzenden Containers anzuzeigen, verwenden Sie die Flagge -p (previous):
    bash kubectl logs <pod-name> -p -n <namespace>

  2. Pod beschreiben: Suchen Sie im Abschnitt Containers nach Restart Count, der angibt, wie oft der Container abgestürzt ist. Überprüfen Sie auch den Last State auf den Exit Code.
    bash kubectl describe pod <pod-name> -n <namespace>
    Ein Exit-Code von 0 bedeutet normalerweise ein ordnungsgemäßes Herunterfahren, aber jeder von Null verschiedene Exit-Code bedeutet einen Fehler. Häufige Nicht-Null-Exit-Codes sind 1 (allgemeiner Fehler), 137 (SIGKILL, oft OOMKilled), 139 (SIGSEGV, Segmentierungsfehler).

Lösung:

  • Anwendungsprotokolle überprüfen: Debuggen Sie Ihren Anwendungscode oder Ihre Konfiguration basierend auf den Protokollen. Stellen Sie sicher, dass alle erforderlichen Umgebungsvariablen, ConfigMaps und Secrets korrekt gemountet/injiziert sind.
  • Lokal testen: Versuchen Sie, das Container-Image lokal mit denselben Umgebungsvariablen und Befehlen auszuführen, um das Problem zu reproduzieren und zu debuggen.

2. Liveness- und Readiness-Probes schlagen fehl

Kubernetes verwendet Liveness- und Readiness-Probes, um die Gesundheit und Verfügbarkeit Ihrer Anwendung zu ermitteln. Wenn eine Liveness-Probe kontinuierlich fehlschlägt, startet Kubernetes den Container neu, was zu CrashLoopBackOff führt.

Diagnose Schritte:

  1. Pod beschreiben: Überprüfen Sie die Liveness- und Readiness-Probendefinitionen und deren Last State im Abschnitt Containers.
    bash kubectl describe pod <pod-name> -n <namespace>
    Suchen Sie nach Meldungen, die auf Probe-Fehler hinweisen, wie z. B. "Liveness probe failed: HTTP probe failed with statuscode: 500".

  2. Anwendungsprotokolle überprüfen: Manchmal liefern die Anwendungsprotokolle Kontext, warum der Probe-Endpunkt fehlschlägt.

Lösung:

  • Probe-Konfiguration anpassen: Korrigieren Sie den path, port, command, initialDelaySeconds, periodSeconds oder failureThreshold der Probe.
  • Gesundheit des Probe-Endpunkts sicherstellen: Überprüfen Sie, ob der von der Probe angesprochene Anwendungsendpunkt tatsächlich gesund ist und wie erwartet antwortet. Die Anwendung startet möglicherweise zu langsam und erfordert einen größeren initialDelaySeconds.

3. Ressourcenlimits überschritten

Wenn ein Container konsistent mehr Arbeitsspeicher als sein memory.limit zu verwenden versucht oder aufgrund der Überschreitung seines cpu.limit CPU-gedrosselt wird, kann der Kernel den Prozess beenden, oft mit einem OOMKilled (Out Of Memory Killed) Ereignis.

Diagnose Schritte:

  1. Pod beschreiben: Suchen Sie im Abschnitt Last State oder Events nach OOMKilled. Ein Exit Code: 137 weist oft auf ein OOMKilled-Ereignis hin.
    bash kubectl describe pod <pod-name> -n <namespace>

  2. kubectl top prüfen: Wenn metrics-server installiert ist, verwenden Sie kubectl top pod, um die tatsächliche Ressourcennutzung Ihrer Pods anzuzeigen.
    bash kubectl top pod <pod-name> -n <namespace>

Lösung:

  • Ressourcenlimits erhöhen: Wenn Ihre Anwendung tatsächlich mehr Ressourcen benötigt, erhöhen Sie die limits für memory und/oder cpu in der Manifestdatei Ihres Pods. Dies erfordert möglicherweise mehr Kapazität auf Ihren Knoten.
    yaml resources: requests: memory: "256Mi" cpu: "500m" limits: memory: "512Mi" # Erhöhen Sie diesen Wert cpu: "1000m" # Erhöhen Sie diesen Wert
  • Anwendung optimieren: Profilieren Sie Ihre Anwendung, um ihren Ressourcenverbrauch zu identifizieren und zu reduzieren.

4. Berechtigungsprobleme

Container können abstürzen, wenn ihnen die erforderlichen Berechtigungen zum Zugriff auf Dateien, Verzeichnisse oder Netzwerkressourcen fehlen.

Diagnose Schritte:

  1. Protokolle überprüfen: Die Anwendungsprotokolle zeigen möglicherweise Berechtigungsverweigerungsfehler (EACCES) an.
  2. Pod beschreiben: Überprüfen Sie das verwendete ServiceAccount und alle gemounteten securityContext-Einstellungen.

Lösung:

  • securityContext anpassen: Setzen Sie runAsUser, fsGroup oder allowPrivilegeEscalation nach Bedarf.
  • ServiceAccount-Berechtigungen: Stellen Sie sicher, dass der mit dem Pod verknüpfte ServiceAccount über die erforderlichen Roles und ClusterRoles verfügt, die über RoleBindings und ClusterRoleBindings gebunden sind.
  • Volume-Berechtigungen: Stellen Sie sicher, dass gemountete Volumes (z. B. emptyDir, hostPath, ConfigMap, Secret) die korrekten Berechtigungen für den Benutzer des Containers haben.

Allgemeine Diagnose Schritte und Werkzeuge

Hier ist eine kurze Checkliste von Befehlen, die Sie ausführen sollten, wenn Sie auf Pod-Probleme stoßen:

  • Schnellen Überblick erhalten: Überprüfen Sie den Status Ihrer Pods.
    bash kubectl get pods -n <namespace> kubectl get pods -n <namespace> -o wide
  • Detaillierte Pod-Informationen: Der wichtigste Befehl zum Verstehen von Pod-Ereignissen, Zuständen und Bedingungen.
    bash kubectl describe pod <pod-name> -n <namespace>
  • Container-Protokolle: Sehen Sie, was Ihre Anwendung meldet.
    bash kubectl logs <pod-name> -n <namespace> kubectl logs <pod-name> -p -n <namespace> # Vorherige Instanz kubectl logs <pod-name> -f -n <namespace> # Protokolle verfolgen
  • Clusterweite Ereignisse: Manchmal liegt das Problem nicht an einem bestimmten Pod, sondern an einem clusterweiten Ereignis (z. B. Knotendruck).
    bash kubectl get events -n <namespace>
  • Interaktives Debugging: Wenn Ihr Container startet, aber schnell abstürzt, können Sie sich möglicherweise kurzzeitig hineinbegeben oder in einen separaten Debug-Container, falls konfiguriert.
    bash kubectl exec -it <pod-name> -n <namespace> -- bash
    (Hinweis: Dies funktioniert nur, wenn der Container lange genug läuft, um sich anzuhängen.)

Best Practices zur Vermeidung von Pod-Problemen

Prävention ist immer besser als Heilung. Die Befolgung dieser Best Practices kann die Vorkommen von Pending und CrashLoopBackOff erheblich reduzieren:

  • Realistische Ressourcenanforderungen und -limits festlegen: Beginnen Sie mit angemessenen requests und limits und optimieren Sie diese dann basierend auf Anwendungs-Profiling und Überwachung.
  • Spezifische Image-Tags verwenden: Vermeiden Sie latest-Tags in der Produktion. Verwenden Sie unveränderliche Tags (z. B. v1.2.3, commit-sha) für die Reproduzierbarkeit.
  • Robuste Probes implementieren: Konfigurieren Sie liveness- und readiness-Probes, die den Gesundheitszustand Ihrer Anwendung genau widerspiegeln. Berücksichtigen Sie Startzeiten mit initialDelaySeconds.
  • Zentralisierte Protokollierung und Überwachung: Verwenden Sie Tools wie Prometheus, Grafana, den ELK-Stack oder Cloud-native Protokollierungsdienste, um Pod-Protokolle und Metriken zu sammeln und zu analysieren.
  • Versionskontrolle für Manifeste: Speichern Sie Ihre Kubernetes-Manifeste in einem Versionskontrollsystem (z. B. Git), um Änderungen zu verfolgen und Rollbacks zu erleichtern.
  • Umfassendes Testen: Testen Sie Ihre Container-Images und Kubernetes-Deployments in Entwicklungs- und Staging-Umgebungen, bevor Sie sie in der Produktion bereitstellen.
  • Ordnungsgemäße Herunterfahren: Stellen Sie sicher, dass Ihre Anwendungen SIGTERM-Signale für ein ordnungsgemäßes Herunterfahren verarbeiten, damit sie Ressourcen vor der Beendigung freigeben können.

Fazit

Das Auftreten von Pods, die in Pending oder CrashLoopBackOff hängen, ist ein häufiges Szenario in Kubernetes-Umgebungen. Obwohl anfangs entmutigend, liefern diese Zustände wertvolle Hinweise. Durch die systematische Untersuchung von Pod-Beschreibungen, Protokollen und Cluster-Ereignissen können Sie die Grundursache ermitteln, sei es eine Ressourcenbeschränkung, ein fehlgeschlagener Image-Pull oder ein Anwendungsfehler. Mit den in dieser Anleitung beschriebenen Diagnose Schritten und Best Practices sind Sie bestens gerüstet, um Ihre Kubernetes-Deployments gesund und Ihre Anwendungen zuverlässig am Laufen zu halten. Viel Spaß beim Debugging!