Docker Rootless 教程:Ubuntu VPS 安装、迁移与排错
在 Ubuntu VPS 上以非 root 用户运行 Docker 守护进程和容器,覆盖 subordinate ID、用户级 systemd、数据迁移、端口映射、资源限制及回滚检查。

Docker Rootless 教程:Ubuntu VPS 安装、迁移与排错
Docker 默认守护进程拥有主机 root 权限,把普通用户加入 docker 组也等同于授予较高的主机控制能力。Rootless mode 的思路不同:守护进程和容器都运行在普通用户的 user namespace 中,降低容器或守护进程漏洞直接取得主机 root 权限的风险。它不是万能隔离层,也不适合所有网络、存储和编排场景;上线前应先核对限制,再从非关键 VPS 迁移。
本文面向 Ubuntu 或 Debian 系 VPS。已有容器的数据保护应先按Docker Compose 数据备份教程完成一致性备份,主机入站端口则可结合nftables 防火墙教程独立管理。Rootless 不能替代备份、防火墙、镜像更新和最小权限。
检查内核与用户映射前提
Docker 官方要求主机具备 newuidmap 和 newgidmap,Ubuntu 通常由 uidmap 包提供。为专用运行用户执行 grep ^用户名: /etc/subuid /etc/subgid,两份文件都应分配足够的 subordinate UID 与 GID 范围;官方示例使用至少 65,536 个映射。不要让多个运行用户复用重叠范围,否则会破坏隔离假设。
建议新建不承担日常登录工作的专用用户,并确认其主目录位于本地文件系统。Rootless 数据目录默认在用户主目录下的 .local/share/docker,官方排错文档指出该目录放在 NFS 上可能引发层文件所有权错误。还要确认系统使用 cgroup v2 和 systemd;如果缺少这些条件,CPU、内存或进程数限制可能不生效。
安装用户级 Docker 守护进程
以目标普通用户登录,在已安装 Docker Engine 软件包的系统上运行 dockerd-rootless-setuptool.sh install。安装器会创建用户级 systemd 单元和名为 rootless 的 Docker CLI context。随后执行 systemctl --user status docker 与 docker context show,确认客户端连接的是用户 socket,而不是误连系统级 /var/run/docker.sock。
要让用户退出登录后服务仍随系统启动,可由管理员执行 loginctl enable-linger 用户名,然后用该用户运行 systemctl --user enable docker。Docker 官方明确说明,不应把 Rootless 守护进程伪装成带 User= 的系统级 docker.service;应使用安装器创建的 ~/.config/systemd/user/docker.service。
若主机原来运行 rootful Docker,不要直接删除旧数据。先停止业务并备份 Compose 文件、环境变量、命名卷和数据库导出,再停止系统级 docker.service 与 docker.socket。Rootless 使用独立的数据目录,原有镜像和容器不会自动出现;应重新拉取镜像、恢复数据并逐个验证服务。确认迁移成功前保留可回滚副本。
处理端口、网络与资源限制
Rootless 网络由 RootlessKit 等用户态组件提供,容器地址不能假定能被主机直接访问,发布服务应使用明确的 -p 或 Compose ports 映射。低于 1024 的特权端口默认受限。更稳妥的做法是在高位端口运行容器,再由 Caddy 或 Nginx 反向代理;若调整系统的非特权端口起点或给 rootlesskit 增加 capability,必须记录扩大后的安全边界。
不要未经 TLS 保护把 Docker API socket 暴露到公网。远程管理优先通过 SSH context,并继续用安全组或 nftables 限制管理入口。Rootless 降低守护进程权限,并不意味着任何能访问该用户 socket 的进程都可以被信任。
资源限制需要 cgroup v2、systemd 和相应 controller 委派。运行 docker info 检查 Cgroup Driver;若显示 none,--cpus、--memory 或 --pids-limit 可能被忽略。再查看用户 slice 的 cgroup.controllers,确认实际委派的控制器。不要只因为命令未报错就认定限制已经生效。
验证、排错与回滚
先运行最小测试容器,再检查重启后的用户服务、端口发布、DNS、卷读写和日志轮转。systemctl --user status docker、journalctl --user-unit docker、docker info 和 docker context ls 是首要排查入口。拉取镜像出现 lchown 错误时,优先检查 subordinate ID 数量和数据目录文件系统;资源参数失效时,检查 cgroup v2 与 controller 委派。
迁移完成后,应确认系统级 Docker socket 已停止,避免 rootful 与 rootless 两套守护进程并存造成误操作。若业务依赖 host 网络、特权端口、复杂存储驱动或严格网络吞吐,应先在隔离环境验证兼容性;无法满足要求时,回滚到经过加固的 rootful Docker 比强行上线更安全。最终目标不是追求“无 root”标签,而是得到权限边界清楚、可恢复、可观察的容器运行环境。


