Skip to main content
Server & DevOpsJune 19, 20265 min read

Kubernetes 1.35 Is the Last Version That Runs containerd 1.x and Most Clusters Have Not Noticed

Kubernetes 1.35, released December 17, 2025, is the last minor release whose runtime support still includes a containerd 1.x version. To upgrade beyond it, every node has to move to containerd 2.x first, and containerd 1.7 itself reaches end of support in September 2026. The trap is not a single date: it is the upgrade path, and most clusters have not noticed because nothing is broken yet.

The change, and the deadline that is really a path

Kubernetes 1.35 shipped on December 17, 2025, and it is the last minor release that still supports a containerd 1.x runtime. From the next Kubernetes minor onward, you are expected to be on containerd 2.x. Separately, the containerd project has already been retiring the 1.x line on its own clock: containerd 1.6 reached end of life on August 23, 2025, and containerd 1.7, the long-term stable branch, is scheduled to reach end of support in September 2026.

The framing that matters: this is not a single calendar instant where everything breaks. It is a property of the upgrade path. As long as you stay on Kubernetes 1.35 or earlier, a node on containerd 1.7 keeps working. The moment you want to move past the last release that supports containerd 1.x, every node has to be on containerd 2.x first. So the real deadline is whichever comes first for you: the day your own upgrade cadence reaches that line, or the September 2026 date after which no one is shipping security fixes for containerd 1.7.

Who is hit hardest, and who can mostly ignore this

The split is clean: managed control planes versus self-managed nodes.

Managed platforms handle the runtime for you

If your nodes are GKE, EKS, or AKS managed node groups, the platform owns the container runtime on the node image and moves it on its own schedule. On GKE, for example, Linux nodes that run GKE 1.33 use containerd 2.0, and the migration from containerd 1.7 happens automatically when the node pool is upgraded to that minor version. GKE documents plainly that you cannot change which containerd version a GKE version uses. That does not mean there is nothing to do, but the work shifts from runtime packaging to compatibility testing, which we get to below.

Self-managed clusters own every node

If you run kubeadm, a bare-metal or VM fleet, k3s or RKE2, or any setup where you install and pin the containerd package yourself, this is squarely your problem. You are responsible for getting containerd 2.x onto every node, in the right order relative to the kubelet, before you cross the upgrade boundary. This is the population most likely to discover the requirement only when a control-plane upgrade refuses to proceed or a freshly upgraded node starts failing. Our Kubernetes management and upgrade service exists for exactly this kind of fleet-wide runtime migration, where the blast radius is every node at once.

What actually breaks on the runtime upgrade

Moving from containerd 1.x to 2.x is a major version bump with two breaking changes that bite real workloads, not just config churn.

First, containerd 2.0 disables pulling Docker Schema 1 images by default. Schema 1 is an old, deprecated image manifest format. If any of your nodes still pull such an image (often an ancient base image, a vendor appliance, or a long-untouched internal artifact), the pull fails after the upgrade. containerd ships an escape hatch, the environment variable CONTAINERD_ENABLE_DEPRECATED_PULL_SCHEMA_1_IMAGE set to 1, but per the containerd documentation that re-enable path is only kept through containerd 2.1. It is a bridge, not a destination. The real fix is to rebuild or re-push the offending images as OCI or Docker Schema 2.

Second, containerd 2.0 removes the deprecated CRI v1alpha2 API. Modern Kubernetes already speaks CRI v1, so the kubelet itself is fine, but older tooling that talks directly to the runtime over the alpha API will stop working. The classic trap is a pinned crictl, a node-level agent, or a custom diagnostic script that still uses v1alpha2.

There is also a quieter, later forcing function on the Kubernetes side. The runtime documentation notes that older containerd versions (1.x and below) do not implement the newer RuntimeConfig CRI call, so the kubelet currently falls back to its own cgroup-driver flag. That fallback is documented to be dropped in Kubernetes 1.38, at which point older containerd will fail outright against newer kubelets. So even setting the support matrix aside, the hard incompatibility is scheduled, not hypothetical.

How to get ready

The work is mostly inventory and ordering, and it rewards being done before the upgrade window rather than during it.

  • Inventory the runtime on every node now. Run crictl version or check the containerd package on each node and find anything still on 1.6 or 1.7.
  • Find Schema 1 images. Audit what your clusters actually pull, including sidecars, init containers, and vendor images, and rebuild or re-tag anything in the old manifest format before you touch the runtime.
  • Find CRI v1alpha2 callers. Check pinned crictl versions, node agents, and any home-grown tooling that connects to the containerd CRI socket directly.
  • Test the runtime upgrade on a canary node pool first, with a representative workload, before rolling it fleet-wide.
  • Confirm your kubelet and containerd versions against the official containerd-to-Kubernetes support matrix for the exact minor you are targeting, not a general assumption.
  • For managed clusters, read your provider's node-image release notes so you know which managed minor flips you to containerd 2.x, and schedule the node-pool upgrade deliberately rather than letting it surprise you.

The honest caveats, so we do not cry wolf

A few things keep this from being a fire drill. The vast majority of modern images are already OCI or Schema 2, so the Schema 1 break affects a long tail, not the median workload. CRI v1alpha2 has been deprecated for years, so most current tooling already speaks CRI v1. And containerd 1.7 is supported through September 2026, which is real runway. The phrasing in the title is deliberate: most clusters have not noticed precisely because, for now, nothing is broken. The risk is not that something fails today. It is that the requirement is invisible until the day you try to upgrade the control plane and the path is blocked, or until the support date passes and you are running an unpatched runtime in production. This is a planning problem disguised as a non-event.

How a senior team de-risks it

The pattern that turns this from a scramble into a non-incident is the same one good platform teams apply to any runtime-level change: decouple the runtime migration from the Kubernetes minor upgrade. Move nodes to containerd 2.x as its own change, on its own canary-then-fleet rollout, while you are still comfortably on a release that supports both. Only after the whole fleet is on 2.x and stable do you proceed with the Kubernetes upgrade that would otherwise have forced the issue under time pressure. That sequencing, plus an image and tooling audit done ahead of the window, is what keeps the September 2026 containerd 1.7 end-of-support date from ever becoming an emergency. It is the same discipline behind staying ahead of managed-platform deadlines generally, as we covered in the EKS extended-support cost cliff: the cost of planning is a few hours of inventory, and the cost of not planning is a blocked upgrade or an unpatched runtime in production.

Sources

Talk to the engineer who will own your stack.

No account managers, no offshore handoff. Senior DevOps, direct. Tell us what you are dealing with and you get a straight answer.