Incident Library
Applied filters SymptomHigh latencyFactorMonitoring blind spotClear allEvery case under the filters, with no sentence; newest first.
Suggested filters Search, and the values found in your words appear here.

Graph

  • Root cause
  • Component
  • Symptom
  • Contributing factor
  • Case

Cases8 cases

6 to 8 of 8

  1. Symptoms

    For about six months, applications on Omio's Google Kubernetes Engine clusters stalled at random: they got stuck, stopped answering health check requests or lost network connections, and nothing the team looked at explained why.

    Trigger

    Multi-threaded workloads running with CPU limits on nodes whose kernel did not yet have the fix for a known CFS quota bug that causes unnecessary throttling.

    Root cause
    Component
    Contributing factor
    Detection

    Months of random stalls and failed health checks led the team to read the cgroup cpu.stat throttling counters inside the pods, which showed far more throttling than the limits should allow.

    Remediation
    • removed CPU limits until the kernel with the CFS bug fix was deployed across all clusters
    Action items
    • Deploy the kernel with the CFS quota bug fix across all clusters
    • Monitor utilisation, saturation and error metrics, API latency and error rates to confirm the change behaves as expected
    Lessons

    A CPU limit is a time quota per 100 ms period, not a share of cores, so a multi-threaded container can be stopped for most of each period long before it uses the cores it was given, and a kernel bug can make that worse. Throttling is invisible in standard Kubernetes metrics and has to be read from the cgroup counters. Removing limits trades away protection against a container that takes a whole node, which is only acceptable when runtimes are tuned.

  2. Symptoms

    The NU.nl development team got reports that several services on one of its Kubernetes clusters behaved erratically: occasional error pages, slow responses and timeouts. The affected services were mostly internal tools and dashboards.

    Trigger

    A new ElastAlert rule, deployed shortly before from the command line, that fired if the Cloudfront-* Elasticsearch indexes stopped receiving documents; those indexes take a few million requests per hour, and the rule made ElastAlert's memory grow without bound.

    Root cause
    Component
    Contributing factor
    Detection

    Users reported error pages, slow responses and timeouts from several services; no alert fired.

    Remediation
    • terminated the NotReady nodes one by one so the auto-scaling group replaced them (the new nodes also went NotReady, but Prometheus and Grafana landed on a stable node)
    • found the ElastAlert pods' memory growth on the Grafana pod memory dashboard
    • fixed the ElastAlert problem that caused the memory growth
    Action items
    • Define alerts on resource usage such as CPU, memory and disk space
    • Keep researching an alerting strategy that combines Elasticsearch, Prometheus Alertmanager and New Relic
    • Consider exporting metrics out of the cluster and running Grafana outside it, on EC2 or a separate Kubernetes cluster
    • Either visualise the important metrics in the ELK stack or make Prometheus and Grafana more available, and improve the metrics strategy
    • Set resource limits for ElastAlert through the Helm values
    • Configure namespaces with default memory requests and limits
    • Isolate customer-facing workloads from build, logging and monitoring workloads (a dedicated node group, or later a separate tools cluster)
    • Deploy everything through automation such as Jenkins pipelines, and consider a GitOps approach
    • Deploy through a pipeline that includes a smoke test step
    • Make Kubernetes and cloud infrastructure work part of the team's sprints, picked up by all team members while pairing with more experienced members, and hold workshops that go deep into specific topics
    Lessons

    Fixing the root cause covers only a small part of what an incident can teach; the chain of smaller failures around it is where most of the learning is. A pod without a memory limit can take whole nodes down, so limits need defaults at the namespace level. Monitoring that runs inside the cluster it watches goes blind with it. Changes installed by hand from the command line leave the rest of the team without a record of what changed.

  3. Symptoms

    After Civis released its new script infrastructure on Kubernetes internally in September 2018, developers reported that kubectl commands were slow, and users intermittently could not start notebooks and services.

    Trigger

    Migrating clients' Python, R and container scripts from the in-house Bocce system to Kubernetes (the project called Croquet) pushed the cluster to about 290 EC2 instances under a large script load.

    Root cause
    Component
    Contributing factor
    Detection

    Developer reports of slow kubectl commands and user reports of notebooks and services failing to start, then high CPU on the master nodes.

    Remediation
    • moved internal users back to the old Bocce infrastructure
    • resized the three master nodes from m4.large to m4.4xlarge
    • changed the Datadog setup so per-node agents no longer polled the API server for service metadata
    • raised max-requests-inflight for non-mutating requests from 400 to 1200
    • grew the etcd EBS volumes from 20 to 100 GB (100 to 300 IOPS)
    • switched client scripts from the ClusterFirst DNS policy to Default
    Action items
    • Upgrade etcd from 2.2.1 to 3.x once Kops supports a safe migration
    • Solve the in-cluster DNS timeouts so client scripts can talk to other workloads in the cluster
    Lessons

    Kubernetes can reach thousands of nodes only after tuning, and third-party DaemonSets are a common cause of control plane load: an agent on every node that polls or watches the API server multiplies with the cluster size. Datadog, kube2iam and the fluentd metadata filter all showed this. A small configuration change often fixes it, but finding it took load testing and the API server access logs.

Check your cluster for this

These 8 cases involve Container CPU limit and kubelet. kubegap audits a Kubernetes cluster for gaps like these, read-only, from Claude Code or Codex; its checks cite public reports like the ones in this library.

By root cause5

Faulty deployment1 case

Organisation
  1. IL-0136 A deployment that cleared an internal service's caches at peak traffic sent 20 times the normal load to the Azure OpenAI metadata backend in Sweden Central, and health checks that depended on its database restarted instances in a loop for almost six hours

Software defect2 cases

Organisation
  1. IL-0124 Capacity changes queued while a circuit breaker was engaged ran all at once when it was released, taking multiple OpenAI inference engines out of service and raising API error rates
    OpenAI2026
  2. IL-0012 CPU limits and an unpatched kernel CFS quota bug throttled multi-threaded services into stalls, failed health checks and timeouts
    Omio2020

Capacity exhaustion3 cases

  1. IL-0181 A traffic spike from an external community post pushed product API pods into CPU throttling under a 1-core limit, and an e-commerce product page slowed down while every pod stayed Running
    Kevin2026
  2. IL-0028 Temporal History service latency rose because its pods were CPU-throttled while CPU usage read below 60 percent
  3. IL-0075 Kubernetes API servers pegged on CPU when the cluster grew to about 290 nodes, traced to Datadog agents polling the API

Cloud provider outage1 case

Organisation
  1. IL-0205 The GKE cluster autoscaler could not add nodes to GitLab.com's production cluster because Google Cloud ran out of SSD persistent disks in us-east1
    GitLab2021

Configuration change1 case

Organisation
  1. IL-0035 Worker nodes went NotReady after a new ElastAlert rule without memory limits used up node memory
    NU.nl2019