Die Kubernetes-Observability-Checkliste für Produktionscluster

Nodes, Workloads, Control Plane, Logs, Traces und Alerts: eine praxisnahe Checkliste, mit der Sie prüfen, ob Ihre Cluster Ihnen im Incident sagen, was Sie wissen müssen.

Lena HoffmannPrincipal SRE, Obseria
Zusammenfassung
  • Kubernetes-Observability braucht Signale aus vier Ebenen: Cluster-Infrastruktur, Kubernetes-Objekte, Workloads und die darin laufenden Anwendungen.
  • Die Checkliste deckt Metriken, Logs, Events und Traces pro Ebene ab, dazu die Alerts, die zuverlässig auf Nutzerauswirkungen hinweisen statt Rauschen zu erzeugen.
  • Einheitliche Ressourcenattribute wie Namespace, Workload und Team verbinden die Ebenen und machen die Ursachenanalyse schnell.

Kubernetes macht das Deployment einfach und das Debugging schwer. Ein langsamer Request kann an der Anwendung liegen, an einem gedrosselten Container, an einem lauten Nachbarn auf demselben Node, an einem DNS-Problem, an einem fehlerhaften Volume oder an einer überlasteten Control Plane. Kubernetes-Observability bedeutet, dass Sie sich zwischen diesen Ebenen in Minuten statt in Stunden bewegen können.

Diese Checkliste verwenden wir selbst, wenn wir Produktionscluster prüfen. Sie ist nach Ebenen gegliedert, und jeder Punkt lässt sich noch heute überprüfen. Nutzen Sie sie als Audit vor der nächsten On-Call-Rotation oder als Zielbild, wenn Sie einen neuen Cluster aufsetzen.

Die vier Ebenen der Kubernetes-Observability

Jedes nützliche Signal in einem Cluster gehört zu einer von vier Ebenen. Lücken entstehen meist dort, wo eine Ebene gut abgedeckt ist und die benachbarte vernachlässigt wird:

EbeneTypische FragenWichtigste Quellen
InfrastrukturSind die Nodes gesund? Gibt es Druck auf Festplatte, Speicher oder Netzwerk?Node-Metriken, Kubelet, APIs des Cloud-Providers
Kubernetes-ObjekteLaufen Deployments mit der gewünschten Replica-Zahl? Hängen Pods in Pending oder starten neu?kube-state-metrics, Kubernetes-Events, API-Server
WorkloadsWerden Container gedrosselt, per OOM beendet oder laufen nah am Limit?cAdvisor über das Kubelet, Container-Logs
AnwendungenSind Nutzer betroffen? Welcher Service verursacht die Latenz?Traces, Anwendungsmetriken, strukturierte Logs

Checkliste: Nodes und Cluster-Infrastruktur

  • Node Conditions werden erfasst und alarmiert: MemoryPressure, DiskPressure, PIDPressure und Ready. Ein Node, der zwischen Ready und NotReady wechselt, erklärt viele scheinbar zufällige Pod-Neustarts.
  • CPU, Speicher, Dateisystem und Netzwerk pro Node sind sichtbar, einschließlich der allokierbaren im Vergleich zur angeforderten Kapazität. Ein Node kann bei 30 % CPU-Auslastung liegen und trotzdem keine Pods mehr aufnehmen, weil die Requests bereits vollständig vergeben sind.
  • Die Nutzung des Ephemeral Storage wird überwacht. Container-Logs und emptyDir-Volumes füllen die Festplatten der Nodes und lösen Evictions aus.
  • Kontext des Cloud-Providers wie Instanztyp, Zone und Node-Pool hängt an jedem Node-Signal, damit Sie erkennen, ob ein Problem auf eine Zone beschränkt ist.
  • Die Aktivität des Cluster Autoscalers ist sichtbar: fehlgeschlagene Scale-ups und Pods, die mangels Kapazität in Pending hängen.

Checkliste: Workloads und Kubernetes-Objekte

  • Neustarts und Beendigungsgründe werden pro Container erfasst, insbesondere OOMKilled, Error und CrashLoopBackOff.
  • CPU-Throttling wird gemessen, nicht nur die CPU-Auslastung. Das Verhältnis gedrosselter Perioden zu allen Perioden deckt zu knappe Limits auf, selbst wenn die durchschnittliche Auslastung unauffällig wirkt.
  • Working Set im Verhältnis zum Memory-Limit wird pro Container überwacht. Das ist der Wert, auf dessen Basis das Kubelet OOM-Entscheidungen trifft, nicht RSS oder Cache.
  • Gewünschte und verfügbare Replicas von Deployments, StatefulSets und DaemonSets werden laufend verglichen.
  • Pods in Pending und deren Gründe (nicht planbar, Fehler beim Image Pull, fehlende Volumes) sind sichtbar.
  • Kubernetes-Events werden gespeichert und nicht nur in kubectl describe angezeigt. Der API-Server hält Events standardmäßig nur kurz vor. Wer sie nicht sammelt, hat sie beim Schreiben des Postmortems nicht mehr.
  • PersistentVolumeClaims melden Kapazität und Nutzung, und fehlgeschlagene Volume-Attachments lösen einen Alert aus.

Mit dem OpenTelemetry Collector stammen die meisten dieser Signale aus drei Receivern. Der kubeletstats-Receiver läuft im DaemonSet, k8s_cluster und k8sobjects laufen in einem Deployment mit einer einzigen Replica, damit clusterweite Daten nicht einmal pro Node erfasst werden:

receivers:
  kubeletstats:
    collection_interval: 30s
    auth_type: serviceAccount
    endpoint: "https://${env:K8S_NODE_NAME}:10250"
    metric_groups: [node, pod, container, volume]
  k8s_cluster:
    collection_interval: 30s
    node_conditions_to_report: [Ready, MemoryPressure, DiskPressure, PIDPressure]
    allocatable_types_to_report: [cpu, memory, ephemeral-storage]
  k8sobjects:
    objects:
      - name: events
        mode: watch
        group: events.k8s.io

Checkliste: Control Plane und Cluster-Dienste

  • Latenz und Fehlerrate des API-Servers werden pro Verb erfasst. Langsame LIST-Aufrufe von Operatoren oder Controllern können den gesamten Cluster ausbremsen.
  • Die Gesundheit von etcd (Leader-Wechsel, Datenbankgröße, fsync-Latenz) wird bei selbst betriebenen Clustern überwacht. Bei Managed Services sollten Sie prüfen, welche Control-Plane-Metriken Ihr Provider bereitstellt.
  • CoreDNS: Anfragerate, Fehlerrate (Spitzen bei SERVFAIL und NXDOMAIN) und Latenz sind sichtbar. DNS-Probleme zeigen sich oft als Timeouts in scheinbar unbeteiligten Services.
  • Ingress Controller und Service Meshes liefern Anfragerate, Fehler und Latenz pro Route und damit eine nutzernahe Sicht am Rand des Clusters.
  • Admission Webhooks werden auf Latenz und Fehler überwacht. Ein langsamer Webhook blockiert jedes Deployment.
  • Ablaufdaten von Zertifikaten für Ingress und interne Kommunikation werden mit ausreichend Vorlauf für die Erneuerung überwacht.

Checkliste: Logs, Traces und Korrelation

  • Container-Logs werden von jedem Node gesammelt, einschließlich der System-Namespaces, und haben eine definierte Aufbewahrungsdauer.
  • Logs sind strukturiert (JSON oder logfmt), wo Sie die Anwendung kontrollieren, und werden geparst, wo das nicht der Fall ist.
  • Jedes Signal trägt dieselben Ressourcenattribute: k8s.cluster.name, k8s.namespace.name, k8s.deployment.name, k8s.pod.name, k8s.node.name sowie ein Team- oder Owner-Label.
  • Traces decken den gesamten Request-Pfad ab, über Ingress, Services und Datenspeicher hinweg, mit OpenTelemetry-SDKs oder Auto-Instrumentierung.
  • Trace-IDs stehen in den Logs, sodass Sie von einem fehlerhaften Span direkt zu den Logzeilen genau dieses Requests springen können.
  • Deployments werden als Events erfasst, mit Version und Commit, damit sich Änderungen mit Regressionen korrelieren lassen.

Container-Logs sammeln Sie mit dem filelog-Receiver und dem container-Parser, der die unterschiedlichen Formate der Container-Runtimes automatisch verarbeitet:

receivers:
  filelog:
    include: [/var/log/pods/*/*/*.log]
    exclude: [/var/log/pods/*/otel-collector/*.log]
    start_at: end
    include_file_path: true
    operators:
      - type: container
        id: container-parser

In Kombination mit dem k8sattributes-Prozessor erhält jede Logzeile Namespace, Workload und Pod. Das ist die Grundlage für jede weitere Abfrage.

Checkliste: Alerts, die zählen

Ein Cluster kann Hunderte Alerts erzeugen, die technisch korrekt und praktisch nutzlos sind. Halten Sie Paging-Alerts nah an der Nutzerauswirkung und leiten Sie alles andere in Tickets oder Dashboards:

  1. Paging bei Symptomen: SLO-Burn-Rate für nutzernahe Services, Fehlerrate und Latenz am Ingress.
  2. Tickets bei Ursachen: Pods länger als zehn Minuten in CrashLoopBackOff, wiederholte OOMKills, anhaltendes CPU-Throttling über 25 %, PVCs mit mehr als 85 % Belegung.
  3. Paging bei Kapazität nur dann, wenn sie die Wiederherstellung blockiert: Pods länger als fünf Minuten in Pending in kritischen Namespaces, Nodes im Zustand NotReady in mehr als einer Zone.
  4. Alerts bei fehlenden Daten: Ein Namespace, der keine Telemetrie mehr sendet, ist selbst ein Problem.

Eine nützliche OQL-Abfrage für Reviews listet die Workloads mit den meisten OOM-Kills der letzten Woche auf und zeigt damit direkt, welche Memory-Limits angepasst werden müssen:

fetch events
| filter k8s.event.reason == "OOMKilling" or container.termination.reason == "OOMKilled"
| summarize kills = count(), by:{k8s.namespace.name, k8s.deployment.name}
| sort kills desc
| limit 15

Die Checkliste im Incident

Ihren Wert zeigt die Checkliste, wenn etwas kaputtgeht. Nehmen wir einen typischen Page: Das Checkout-SLO verbraucht Error Budget, und die Latenz am Ingress hat sich verdoppelt. Sind alle vier Ebenen abgedeckt, folgt die Analyse einem vorhersehbaren Pfad statt einer Reihe von Vermutungen:

  1. Anwendungsebene: Die Traces langsamer Checkout-Requests zeigen, dass die Zeit im Inventory-Service verbracht wird, nicht im Checkout selbst.
  2. Workload-Ebene: Die Inventory-Container zeigen seit dem letzten Deployment ein CPU-Throttling von über 40 %, während die durchschnittliche CPU-Auslastung unauffällig aussieht.
  3. Kubernetes-Objekte: Das Deployment-Event zeigt eine neue Version mit reduziertem CPU-Limit, eingeführt durch eine Änderung an einem gemeinsam genutzten Helm-Chart.
  4. Infrastruktur: Die Node-Metriken bestätigen, dass es keinen Druck auf Node-Ebene gibt. Ein lauter Nachbar oder ein defekter Node scheidet damit aus.

Jeder Schritt braucht nur eine einzige Abfrage, weil die Signale dieselben Ressourcenattribute teilen. Ohne gespeicherte Events wäre das Deployment unsichtbar, ohne Throttling-Metriken sähe der CPU-Graph gesund aus, ohne Trace-Kontext begänne die Suche im falschen Service. Jede Lücke in der Checkliste verwandelt einen dieser Schritte in eine lange manuelle Suche, und genau dort gehen Stunden an MTTR verloren.

Checkliste: Kosten und Effizienz

  • Requests und tatsächliche Nutzung werden pro Workload regelmäßig verglichen. Überdimensionierte Requests verschwenden Node-Kapazität, unterdimensionierte führen zu Throttling und Evictions.
  • Ungenutzte Namespaces und verwaiste Ressourcen (nicht verwendete PVCs, Load Balancer ohne Backends) werden gemeldet.
  • Das Telemetrievolumen pro Namespace ist bekannt, damit sich geschwätzige Workloads angehen lassen, bevor sie die Observability-Kosten treiben.
  • Health-Check-Traffic wird in der Pipeline aus Traces und Logs herausgefiltert.

Kubernetes-Observability mit Obseria

Der Obseria Agent wird einmal pro Node als DaemonSet installiert und erfasst Node-, Pod- und Container-Metriken, Logs, Traces und Profile, jeweils automatisch mit Kubernetes-Metadaten versehen. Obseria TopoGraph bildet die Beziehungen zwischen Clustern, Nodes, Workloads und Services ab. Ein Alert auf dem Checkout-Service führt so direkt zum gedrosselten Container und zu dem Node, auf dem er läuft. Bestehende OpenTelemetry-Collector-Deployments können OTLP direkt senden, die Receiver-Konfigurationen von oben funktionieren unverändert.

Unabhängig von Ihren Werkzeugen: Gehen Sie diese Checkliste einmal pro Quartal durch. Cluster verändern sich, neue Workloads kommen hinzu, und Lücken entstehen meist dort, wo gerade niemand hinsieht.

Teilen

Lena Hoffmann

Principal SRE, Obseria

Observability, die Antworten liefert.

Starten Sie kostenlos mit OpenTelemetry, ohne Kreditkarte.