PAYATHON 2026

使用 Bind Mount 的 Docker WordPress 容器无法停止或删除,如何排查?

数据小陈

容器使用 Bind Mount,不能据此判断停止失败是挂载目录权限造成的。当前报错来自 Docker daemon 的停止操作,应先检查 daemon、容器运行时和宿主机安全策略。仅凭这份配置和报错,还无法确定具体原因。

sudo docker rm -f 也不能绕过运行时或内核层面的权限限制。需要先确认失败发生在哪一层,再处理对应问题。

1. 确认连接的是哪个 Docker daemon

在执行原命令的终端中运行:

docker context show
docker context inspect
docker info
docker compose ps -a

确认当前 context 指向的 Docker endpoint,以及 xkcd-wordpress-1 是否属于当前 Compose 项目。如果连接的是远程 daemon,后续应在远程宿主机上检查服务和内核日志。

如果要比较普通用户与 sudo 下的行为,还应检查:

sudo docker context show
sudo docker info

普通用户和 root 可能使用不同的配置或 endpoint。确认连接的是同一个 daemon 后,才能比较两种执行方式的结果。

这里的报错是 Error response from daemon: cannot stop container,表明请求已经到达 daemon。这与客户端无法访问 Docker socket 时的权限错误不同,不能直接把“加入 docker 用户组”当作修复办法。

2. 查看容器状态和停止失败时的日志

以下命令中的容器名应替换为实际失败的容器:

docker inspect --format '{{json .State}}' xkcd-wordpress-1
docker inspect --format '{{.AppArmorProfile}}' xkcd-wordpress-1
docker inspect --format '{{json .Mounts}}' xkcd-wordpress-1

这些信息有助于确认容器状态、PID、AppArmor profile 和实际挂载路径,但通常不能单凭这些输出确定原因。docker logs 可以补充容器内的应用信息;排查停止操作失败时,应重点查看 daemon 和运行时日志。

如果宿主机使用 systemd,且运行的是系统级 Docker 服务,可以检查:

sudo journalctl -u docker.service -u containerd.service --since '15 minutes ago' --no-pager
sudo journalctl -k --since '15 minutes ago' --no-pager

对照停止失败的时间,查找 permission denied、denied、apparmor、avc、runc 或 containerd 等记录。如果没有独立的 containerd.service,需要按实际安装方式查找运行时日志。

如果使用的是由 systemd 用户服务管理的 rootless Docker,应在对应用户下检查:

journalctl --user -u docker.service --since '15 minutes ago' --no-pager

3. 根据日志处理权限或运行时问题

如果日志中有 AppArmor 拒绝记录,应结合时间、进程、profile 和被拒绝的操作,确认是否对应本次停止请求,再修复相关策略或安装配置。SELinux 环境下也应依据对应的 AVC 记录处理。不要仅凭 permission denied 就关闭整套安全机制。

如果日志显示运行时通信失败、状态异常或服务故障,可以在确认对其他容器的影响并安排维护窗口后,重启相关服务。对于系统级 Docker,常见操作是:

sudo systemctl restart docker.service

重启 Docker 可能影响同一 daemon 管理的其他服务,也不保证能解决安全策略拒绝。如果错误仍然存在,应继续依据新日志排查,避免反复强制删除。

4. 区分挂载目录权限与停止操作权限

以下映射让容器内进程访问宿主机目录:

- /home/nitin/Documents/wp/wwwroot:/var/www/html
- /home/nitin/Documents/wp/database:/var/lib/mysql

目录权限不匹配的常见表现是 WordPress 无法写入文件,或 MySQL 无法访问数据文件。要判断是否属于这种情况,需要查看应用日志、目录所有权,以及容器进程实际使用的 UID/GID。

不要为了修复停止失败,直接对这些目录执行 chmod -R 777、递归 chown 或删除数据库目录。这些操作可能改变数据访问条件,却不能针对性解决运行时停止容器时的权限错误。

5. 修复后重新停止并删除容器

在正确的 Compose 项目目录中,使用原部署时相同的配置文件和项目参数执行:

docker compose down

如需单独处理已确认的容器,可以执行:

docker stop xkcd-wordpress-1
docker rm xkcd-wordpress-1

docker rm -f 仍依赖 daemon 和运行时执行终止操作。如果这一层持续返回 permission denied,重复执行通常不会消除根因。

成功执行 docker compose down 后,Bind Mount 对应的宿主机文件仍会保留,包括 wwwroot、database 和 php.ini。删除容器与删除这些数据是两项独立操作。

另外,粘贴的 Compose 配置缺少 YAML 层级缩进。如果实际文件也是这样,需要修正,并运行 docker compose config 检查解析结果。当前日志已经进入停止已有容器的阶段,不能把粘贴格式问题直接认定为这次停止失败的原因;配置检查通过也不能证明运行时权限正常。

备注:内容仅供参考。