Rootless Docker & Podman
Remove the root daemon from the picture entirely.
Hardening containers still leaves one enormous target: the Docker daemon itself, which traditionally runs as root. Every container it launches is a child of a root process, and anyone who can reach its socket can become root on the host. Rootless mode removes that premise — it runs the entire daemon and all containers as an unprivileged user, using a user namespace so “root” inside a container maps to your ordinary UID outside. A daemon compromise is then a user compromise, not a host takeover.
$ dockerd-rootless-setuptool.sh install # sets up a per-user rootless daemon$ docker context use rootless$ docker run --rm alpine id # "root" in the container...uid=0(root)$ ps -o user= -p $(pgrep -f dockerd) # ...but the daemon runs as youyou
What rootless changes, and what it costs
The benefit is structural: the daemon holds no root privilege, so the worst case shrinks dramatically. The costs are real but usually acceptable — binding ports below 1024 needs an extra setcap or a sysctl, some storage drivers and networking modes are limited, and a few features (certain cgroup controls, AppArmor nuances) differ. For most application workloads none of that bites, and the reduction in blast radius is worth it.
Podman: daemonless by design
Podman takes the idea further: it is rootless by default and has no central daemon at all — each container is a direct child of the CLI invocation, so there is no long-running root service to attack, and containers integrate cleanly with systemd for supervision. Its CLI is deliberately Docker-compatible (alias docker=podman largely works), which makes it a low-friction way to get both rootless and daemonless in one move.