This post is for Linux users running Docker Engine (Community Edition) directly on their hosts. Docker Desktop users don’t need to take any action — Engine updates are included automatically in future Desktop releases.
Docker Engine v29 is a foundational release that sets the stage for the future of the Docker platform. While it may not come with flashy new features, it introduces two significant under-the-hood changes that simplify our architecture and improve ecosystem alignment:
- The Containerd image store is now the default for new installations.
- Migration to Go modules
- Experimental Support for NFTables
These changes improve maintainability, developer experience, and interoperability across the container ecosystem.
Containerd Image Store Becomes the Default
Why We Made This Change
The Containerd runtime originated as a core component of Docker Engine and was later split out and donated to the Cloud Native Computing Foundation (CNCF). It now serves as the industry-standard container runtime, powering Kubernetes and many other platforms.
While Docker introduced containerd for container execution years ago, we continued using the graph driver storage backend for managing image layers. Meanwhile, containerd evolved its own image content store and snapshotter framework, designed for modularity, performance, and ecosystem alignment.
To ensure stability, Docker has been gradually migrating to the containerd image store over time. Docker Desktop has already used the containerd image store as the default for most of the past year. With Docker Engine v29, this migration takes the next step by becoming the default in the Moby engine.
What it is
- As of Docker Engine v29, the containerd image store becomes the default for image layer and content management for new installs.
- Legacy graph drivers are still available, but are now deprecated. New installs can still opt out of Containerd image store if there is any issue.
Why This Matters
- Simplified architecture: Both execution and storage now use containerd, reducing duplication and internal complexity
- Unlock new feature possibilities, such as:
- Snapshotter innovations
- Lazy pulling of image content
- Remote content stores
- Peer-to-peer distribution
- Ecosystem alignment: Brings Docker Engine in sync with containerd-based platforms, like Kubernetes, improving interoperability.
- Future-proofing: Enables faster innovation in image layer handling and runtime behaviour
We appreciate that this change may cause some disruption, as the Containerd image store takes a different approach to content and layer management compared to the existing storage drivers.
However, this shift is a positive one. It enables a more consistent, modular, and predictable container experience.
Migration Path
To be clear, these changes only impact new installs; existing users will not be forced to containerd. However, you can start your migration now and opt-in.
We are working on a migration guide to help teams transition and move their existing content to the containerd image store.
What’s next
- The graph driver backend will be removed in a future release.
- Docker will continue evolving the image store experience, leveraging the full capabilities of containerd’s ecosystem.
- Expect to see enhanced content management, multi-snapshotter support, and faster pull/push workflows in the future.
Moby Migrates to Go Modules
Why We Made This Change
Go modules have been the community standard since 2019, but until now, the Moby project used a legacy vendoring system. Avoiding Go modules was creating:
- Constant maintenance churn to work around tooling assumptions
- Confusing workflows for contributors
- Compatibility issues with newer Go tools and ecosystem practices
Simply put, continuing to resist Go modules was making life harder for everyone.
What It Is
- The Moby codebase is now fully module-aware using go.mod.
- This means cleaner dependency management and better interoperability for tools and contributors.
- External clients, API libraries, and SDKs will find the Moby codebase easier to consume and integrate with.
What It’s Not
- This is not a user-facing feature—you won’t see a UI or command change.
- However, it does affect developers who consume Docker’s Go APIs.
Important for Go Developers
If you’re consuming the Docker client or API packages in your own Go projects:
- The old module path github.com/docker/docker will no longer receive updates.
- To stay current with Docker Engine releases, you must switch to importing from github.com/moby/moby.
Experimental support for nftables
Why We Made This Change
For bridge and overlay networks on Linux, Docker Engine currently creates firewall rules using “iptables” and “ip6tables”.
In most cases, these commands are linked to “iptables-nft” and “ip6tables-nft”. So, Docker’s rules are translated to nftables behind the scenes.
However, OS distributions are beginning to deprecate support for iptables. It’s past time for Docker Engine to create its own nftables rules directly.
What It Is
Opt-in support for creating nftables rules instead of iptables.
The rules are functionally equivalent, but there are some differences to be aware of, particularly if you make use of the “DOCKER-USER” chain in iptables.
On a host that uses “firewalld”, iptables rules are created via firewalld’s deprecated “direct” interface. That’s not necessary for nftables because rules are organised into separate tables, each with its own base chains. Docker will still set up firewalld zones and policies for its devices, but it creates nftables rules directly, just as it does on a host without firewalld.
What It’s Not
In this initial version, nftables support is “experimental”. Please be cautious about deploying it in a production environment.
Swarm support is planned for a future release. At present, it’s not possible to enable Docker Engine’s nftables support on a node with Swarm enabled.
In a future release, nftables will become the default firewall backend and iptables support will be deprecated.
Future Work
In addition to adding planned Swarm support, there’s scope for efficiency improvements.
For example, the rules themselves could make more use of nftables features, particularly sets of ports.
These changes will be prioritised based on the feedback received. If you would like to contribute, do let us know!
Try It Out
Start “dockerd” with option “--firewall-backend=nftables” to enable nftables support.
After a reboot, you may find you need to enable IP Forwarding on the host. If you’re using the “DOCKER-USER” iptables chain, it will need to be migrated. For more information, see https://docs.docker.com/engine/network/firewall-nftables
We’re looking for feedback. If you find issues, let us know at https://github.com/moby/moby/issues.
Getting Started with Engine v29
As mentioned, this post is for Linux users running Docker Engine (Community Edition) directly on their hosts. Docker Desktop users don’t need to take any action — Engine updates are included automatically in the upcoming Desktop releases.
To install Docker Engine on your host or update an existing installation, please follow the guide for your specific OS.
For additional information about this release: