
Docker 磁盘明明迁到大盘了df 却显示还在根分区聊聊 containerd snapshotter 这个坑一次惊悚的rm -rf /var/lib/docker/*引发的排查实录data-root 配了、目录迁了、du 也对得上但磁盘账目就是不平。最后发现是新版 Docker 的 containerd snapshotter 在作妖镜像层根本不看>目录事故起因一把 rm -rf 引发的虚惊第一个疑点容器为什么没死第二个疑点磁盘账目对不上真凶浮现mount 输出出卖了一切原理data-root 到底管什么迁移 Runbook完整可复制迁移后的第一个坑compose 网络总结一张账目表 三条红线一、事故起因一把 rm -rf 引发的虚惊线上服务器根分区常年告急同事之前把 Docker 的data-root改到了大盘/data几百 G 空闲以为迁移完成。为了给根分区腾空间执行了rm-rf/var/lib/docker/*然后docker ps一看容器全在跑一个没死。有人会说这不是好事吗不。这恰恰说明磁盘账目对不上如果 Docker 数据真在/var/lib/docker这一把下去容器早炸了。没炸说明你以为的数据位置和真实的数据位置不是同一个地方。先给同样手痒的朋友提个醒这次是运气好删的恰好是空壳。如果你的环境>二、第一个疑点容器为什么没死三组命令定位 Docker 的真实存储位置# 1. Docker 声明的根目录dockerinfo--format{{.DockerRootDir}}# 输出/data/docker# 2. 老目录还剩什么ls-la/var/lib/docker/readlink-f/var/lib/docker# 输出空目录4.0K无软链# 3. 两边各占多少du-sh/data/docker /var/lib/docker# 9.7G /data/docker# 4.0K /var/lib/docker看起来很美好DockerRootDir指向大盘老目录是空壳数据 9.7G 落在/data/docker。到这里我差点就收工了。但磁盘账目对不上。三、第二个疑点磁盘账目对不上看df -h/dev/sda2 98G 40G 54G 43% / ← 根分区 /dev/sda3 492G 513M 466G 1% /data ← 大盘 overlay 98G 40G 54G 43% ... ← 容器层挂载显示 98G三个矛盾点现象预期实际/data大盘已用≥ 9.7G513Moverlay 挂载的 Size492G在 sda3 上98G 根分区du /data/docker和 df 一致9.7G但 sda3 没涨9.7G 的 Docker 数据物理上根本不在大盘上还压在根分区里。du是穿过 overlay 挂载点统计的容器内文件视图被它骗了。四、真凶浮现mount 输出卖出了一切mount|grepoverlay|head-2输出截取关键部分overlay on /data/docker/rootfs/overlayfs/a1b2c3d4e5f6... type overlay (rw,relatime, lowerdir/var/lib/containerd/io.containerd.snapshotter.v1.overlayfs/snapshots/2998/fs:..., upperdir/var/lib/containerd/io.containerd.snapshotter.v1.overlayfs/snapshots/3000/fs, workdir/var/lib/containerd/io.containerd.snapshotter.v1.overlayfs/snapshots/3000/work,nouserxattr)所有容器的 lowerdir、upperdir 全在/var/lib/containerd也就是根分区。挂载点在/data/docker/rootfs/...只是个门面。再确认规模和管理方式du-sh/var/lib/containerd# 24G ← 根分区 40G 已用里的大头就是它ps-ef|grep[c]ontainerd# root 3252 1 /usr/bin/containerd ← 独立 systemd 服务# root ... /usr/bin/dockerd --containerd/run/containerd/containerd.sock真相大白。五、原理data-root 到底管什么这是新版 Docker 的一个知名坑GitHub 上有大量 issueDocker 启用了 containerd snapshotter 作为镜像存储后端。在这个架构下两套存储各管各的存储位置管什么听谁的Docker>dockerinfo--format{{.DriverStatus}}|grep-icontainerd# 有 containerd-snapshotter 字样 中招六、迁移 Runbook完整可复制前提确认containerd 是独立 systemd 服务ps能看到/usr/bin/containerd由 1 号进程拉起。如果是 Docker 内嵌拉起的daemon.json没有对应配置项直接用软链接方案文末附。① 迁移前快照cat/etc/containerd/config.toml2/dev/null||echo无配置文件跑的默认值systemctl status containerd --no-pager|head-5② 停服务顺序不能乱cd你的 compose 项目目录dockercompose stop systemctl stopdockerdocker.socket systemctl stop containerd③ 拷贝数据保属性24G 几分钟到十几分钟rsync-aHAX/var/lib/containerd/ /data/containerd/中断了直接重跑rsync 增量续传安全。④ 写配置root 指向大盘没有配置文件就创建最小配置cat/etc/containerd/config.tomlEOF version 2 root /data/containerd EOF已有配置文件的话只改第一处root ...别动其他配置项比如 CRI、snapshotter、registry 相关动了可能起不来。⑤ 老目录改名做备份先不删mv/var/lib/containerd /var/lib/containerd.bak⑥ 起服务并验证systemctl start containerd systemctl startdockerdockerimages# 镜像列表完整df-h/ /data# 根分区下降/data 上涨mount|grepoverlay|head-1# lowerdir/upperdir 变成 /data/containerd/...⑦ 观察一两天确认无异常后清备份rm-rf/var/lib/containerd.bak回滚方案任何一步翻车时systemctl stopdockerdocker.socket containerdrm/etc/containerd/config.toml# 或改回原 rootmv/var/lib/containerd.bak /var/lib/containerd systemctl start containerdsystemctl startdocker七、迁移后的第一个坑compose 网络迁移本身成功后起容器时可能撞上Error response from daemon: failed to set up container networking: network f0e1d2c3b4a5... not found原因Docker 重启后 compose 的自定义网络被重建新 ID但没被 recreate 的旧容器还引用旧网络 ID。跟迁移本身无关是重启后的常见现象。解法整体重建volumes 不受影响。dockercompose downdockercompose up-d# down 也报网络错误时用强制版dockercompose down --remove-orphans --force-recreatedockercompose up-d八、总结一张账目表 三条红线磁盘账目迁移前后迁移前迁移后根分区已用40Gcontainerd 24G 在内~16G.bak 删掉后大盘已用513M~25G容器层物理位置/var/lib/containerd/data/containerd三条红线/var/lib/containerd是镜像和容器的真身。rm -rf /var/lib/docker中招 containerd snapshotter 模式时是删了个寂寞但rm -rf /var/lib/containerd是真删家。删除前必跑docker info --format {{.DockerRootDir}}mount | grep overlay。验证迁移别信 du信 mount。du 会穿透 overlay 挂载点mount | grep overlay的 upperdir 路径才是数据物理位置。跨文件系统 mv 不是原子操作中途别 CtrlC断了用 rsync 续。附containerd 为 Docker 内嵌时的软链接方案systemctl stopdockerdocker.socketmv/var/lib/containerd /data/containerdln-s/data/containerd /var/lib/containerd systemctl startdocker改动最小但对 systemd 升级、containerd 包更新兼容性略差能用配置迁移就别用软链。环境Ubuntu 22.04 / Docker 27 containerd snapshotter / overlay2。命令和输出均为实际排查记录整理主机名和业务信息已脱敏。