我通过 systemd 单元处理由 docker 容器实现的许多服务(数据库、Web 服务器...)。它可以工作,但是系统关闭需要很长时间,显然是在等待 docker 服务关闭。
下面是我在 Debian Stretch 下的虚拟机中使用 Docker CE 创建的 systemd 单元的示例:
/lib/systemd/system/mariadb.service
[Unit]
Description=MariaDB
After=docker.service
Requires=docker.service
[Service]
TimeoutStartSec=0
Restart=always
ExecStart=/usr/bin/docker run --rm \
--name=mariadb \
-p 3306:3306 \
-e MYSQL_ROOT_PASSWORD=root \
-e MYSQL_DATABASE=test \
-e MYSQL_USER=user \
-e MYSQL_PASSWORD=user \
-v /var/lib/mysql:/var/lib/mysql \
mariadb:latest
ExecStop=-/usr/bin/docker stop mariadb # See UPDATEs 1 & 2
[Install]
WantedBy=multi-user.target
当我使用 systemctl 命令时,服务会在几秒钟内正常启动和停止。但是当我关闭系统时,它显示:
持续时间超过 3 分钟。如果有许多通过 systemd 运行的容器,则时间可能会更长。
该问题并非 MariaDB 所特有。
有没有更好的方法通过 systemd 处理 docker 容器,避免额外的关机时间?
更新 1:正如 Bennett Hardwick 在评论中所建议的那样,我尝试从服务定义中删除 ExecStop 指令。这样似乎更好,因为服务会在 1 分 30 秒后停止,而不是 3 分钟。
更新2:我尝试在ExecStop指令中向docker stop命令添加选项-t(https://docs.docker.com/engine/reference/commandline/stop/)。没有效果。
答案1
不再维护的解决方案是 systemd-docker, 被形容为:
这是 docker run 的包装器,以便您可以在 systemd 下合理地运行 Docker 容器。此包装器的关键功能是将容器进程从 Docker 设置的 cgroups 移至服务单元的 cgroup。这处理了许多其他怪癖,因此请通读文档以了解在 systemd 下运行 Docker 的所有含义。
使用此包装器,您可以通过 systemctl 或 docker CLI 管理容器,并且所有内容都应保持同步。此外,您还可以利用 systemd 和 systemd-notify 的所有 cgroup 功能。
这篇文章讨论了如何让 systemd-docker 与最新的 Linux 版本兼容的问题 不适用于最新的 systemd 和/或 docker 版本,其中名为 james-cxx 的用户报告了成功:
我可以通过以下方式让 systemd-docker 与 Ubuntu 18.04 一起工作:
- 从头开始构建 systemd-docker@agend07 的分支,根据@agend07 和@Halfwalker 上述讨论。
--cgroups name=systemd
在systemd-docker
单元文件中 添加https://container-solutions.com/running-docker-containers-with-systemd/我的猜测docker 默认不使用 systemd 进行 cgroups 操作,因为“委托问题仍然存在,并且 systemd 目前不支持 docker 运行的容器所需的 cgroup 功能集”(根据 docker.service 单元文件),而我预计 systemd-docker 需要使用 systemd 进行 cgroups 操作,因此出现错误
open /sys/fs/cgroup/system.slice/docker.service/cgroup.procs: no such file or directory
。设置--cgroups name=systemd
显然会覆盖 docker 默认设置,但是,鉴于 docker.service 单元文件中的不祥提示,我无法说出这可能会产生什么副作用。
systemd-docker 的替代方案可能是使用 韋克, 被形容为:
rkt 是为现代生产云原生环境开发的应用程序容器引擎。它采用 pod 原生方法、可插入执行环境和定义明确的表面区域,非常适合与其他系统集成。