Veröffentlicht am

Kubernetes Endpoint Not Ready: Service ohne Endpoints debuggen

Teilen:
Authors

Kubernetes Endpoint Not Ready: Service ohne Endpoints debuggen

TL;DR

Service ohne Endpoints? Drei Dinge prüfen: Stimmen die Label-Selektoren zwischen Service und Pod überein? Sind die Readiness Probes erfolgreich? Passt der targetPort im Service zum containerPort im Pod? kubectl get endpoints <service> zeigt sofort, ob Endpoints registriert sind.


Woran erkennen Sie das Problem?

Ihre Anwendung ist nicht erreichbar, obwohl der Pod läuft. curl auf den Service gibt Connection Refused oder Timeouts. Der erste Diagnose-Befehl:

# Endpoints des Service prüfen
kubectl get endpoints my-service -n default

# Erwartete Ausgabe wenn alles OK:
# NAME         ENDPOINTS           AGE
# my-service   10.244.1.5:8080     2d

# Ausgabe bei Problem:
# NAME         ENDPOINTS   AGE
# my-service   <none>      2d

<none> bei ENDPOINTS bedeutet: Kein einziger Pod ist dem Service zugeordnet. Kein Traffic wird weitergeleitet.

Die 3 häufigsten Ursachen

1. Label-Selektor stimmt nicht überein

Das ist mit Abstand die häufigste Ursache. Der Service sucht Pods anhand von Labels -- und findet keine.

# Service-Selektor anzeigen
kubectl get service my-service -o jsonpath='{.spec.selector}' | jq .
# Ausgabe: {"app": "my-app"}

# Pods mit diesem Label suchen
kubectl get pods -l app=my-app -n default
# Keine Ergebnisse? Dann stimmt das Label nicht.

# Tatsächliche Labels der Pods prüfen
kubectl get pods -n default --show-labels

Ein klassischer Fehler: Das Deployment nutzt app: myapp (ohne Bindestrich), der Service sucht nach app: my-app (mit Bindestrich). Kubernetes meldet keinen Fehler -- der Service hat einfach keine Endpoints.

Fix:

# Service-Selektor muss exakt zu den Pod-Labels passen
apiVersion: v1
kind: Service
metadata:
  name: my-service
spec:
  selector:
    app: myapp          # Muss mit Pod-Labels übereinstimmen
  ports:
  - port: 80
    targetPort: 8080

2. Readiness Probe schlägt fehl

Pods existieren und Labels stimmen, aber die Endpoints zeigen NotReady. Das bedeutet: Die Readiness Probe des Containers schlägt fehl, und Kubernetes nimmt den Pod aus dem Service-Traffic.

# Detaillierte Endpoint-Informationen mit NotReady-Adressen
kubectl get endpointslices -l kubernetes.io/service-name=my-service -o yaml

# Pod-Events prüfen -- hier sehen Sie Readiness-Probe-Fehler
kubectl describe pod <pod-name> -n default | grep -A 5 "Readiness"

Typische Events bei Readiness-Probe-Fehlern:

Warning  Unhealthy  Readiness probe failed: HTTP probe failed with statuscode: 503
Warning  Unhealthy  Readiness probe failed: dial tcp 10.244.1.5:8080: connect: connection refused
Readiness-FehlerUrsacheLösung
HTTP 503Anwendung nicht bereitStartup-Zeit prüfen, initialDelaySeconds erhöhen
Connection refusedContainer-Port falschcontainerPort im Pod prüfen
TimeoutProbe zu kurztimeoutSeconds erhöhen
Command failedExec-Probe gibt Exit Code != 0Probe-Command im Container testen

Fix: Readiness Probe anpassen

spec:
  containers:
  - name: app
    readinessProbe:
      httpGet:
        path: /healthz
        port: 8080
      initialDelaySeconds: 15    # Anwendung braucht Zeit zum Starten
      periodSeconds: 5
      timeoutSeconds: 3          # Timeout großzügiger setzen
      failureThreshold: 3

3. Port-Mismatch

Der Service leitet Traffic an einen Port weiter, auf dem der Container nicht lauscht.

# Service-Ports prüfen
kubectl get service my-service -o jsonpath='{.spec.ports[*]}' | jq .

# Container-Ports prüfen
kubectl get pod <pod-name> -o jsonpath='{.spec.containers[*].ports[*]}' | jq .

Der targetPort im Service muss mit dem containerPort im Pod übereinstimmen:

# Service
spec:
  ports:
  - port: 80            # Port des Service (für andere Pods/Ingress)
    targetPort: 8080     # Muss zum containerPort passen!

# Pod/Deployment
spec:
  containers:
  - name: app
    ports:
    - containerPort: 8080   # Hier muss die App tatsächlich lauschen

Tipp: Testen Sie direkt im Pod, ob die Anwendung auf dem richtigen Port läuft:

# Port-Check direkt im Container
kubectl exec <pod-name> -- ss -tlnp
# oder
kubectl exec <pod-name> -- netstat -tlnp

Debugging-Workflow: Schritt für Schritt

Wenn die Ursache nicht offensichtlich ist, dieser Workflow:

# 1. Hat der Service Endpoints?
kubectl get endpoints my-service

# 2. Selektor des Service
kubectl get svc my-service -o jsonpath='{.spec.selector}'

# 3. Pods mit diesem Selektor
kubectl get pods -l $(kubectl get svc my-service -o jsonpath='{range .spec.selector}{@}' | sed 's/map\[//;s/\]//;s/ /,/g;s/:/=/g')

# 4. Readiness-Status der Pods
kubectl get pods -l app=myapp -o jsonpath='{range .items[*]}{.metadata.name}{"\t"}{.status.conditions[?(@.type=="Ready")].status}{"\n"}{end}'

# 5. Connectivity-Test zum Pod direkt (ohne Service)
kubectl run test-curl --image=curlimages/curl --rm -it --restart=Never -- curl -v http://<pod-ip>:8080/healthz

Sonderfall: Headless Service

Bei Headless Services (clusterIP: None) gibt es keine virtuelle Service-IP. DNS gibt die Pod-IPs direkt zurück. Wenn Endpoints fehlen, gelten dieselben Debugging-Schritte. Aber Vorsicht: Bei StatefulSets muss der Pod Ready sein, damit der DNS-Eintrag existiert.

# DNS-Auflösung eines Headless Service testen
kubectl run dns-test --image=busybox --rm -it --restart=Never -- nslookup my-service.default.svc.cluster.local

FAQ

Mein Pod ist Ready, aber der Endpoint zeigt trotzdem NotReady?

Prüfen Sie, ob publishNotReadyAddresses: true im Service gesetzt ist. Ohne dieses Feld werden nur Ready-Pods als Endpoints registriert. Selten kann auch ein veralteter EndpointSlice-Controller das Problem sein -- starten Sie den kube-controller-manager Pods neu.

Kann ich Traffic auch an nicht-ready Pods schicken?

Ja, mit service.spec.publishNotReadyAddresses: true. Das ist nützlich für StatefulSets, bei denen Pods sich gegenseitig für die Cluster-Bildung erreichen müssen, bevor sie Ready werden.

Wie teste ich, ob der Service Traffic weiterleitet?

Starten Sie einen temporären Pod im Cluster und curlen Sie den Service: kubectl run test --image=curlimages/curl --rm -it --restart=Never -- curl -v http://my-service:80. Das testet DNS-Auflösung und Service-Routing in einem Schritt.

Mein Ingress gibt 503 zurück -- liegt das am Endpoint?

Oft ja. Ein 503 vom Ingress Controller bedeutet meistens, dass der Backend-Service keine ready Endpoints hat. Debuggen Sie zuerst den Service mit den Schritten oben, bevor Sie den Ingress prüfen.


Wenn Ihr Service erreichbar ist, aber 502/503/504 Fehler zurückgibt, liegt das Problem oft am Ingress Controller. Unser Ingress Troubleshooting Guide hilft bei der Diagnose.

Kubernetes-Beratung gesucht?

Wir helfen deutschen Unternehmen bei der Kubernetes-Implementierung, Migration und Optimierung. DSGVO-konform und praxiserprobt.

📖 Verwandte Artikel

Weitere interessante Beiträge zu ähnlichen Themen