Docker 持久性中的 PID 1
PID 1 in Docker persistance
我已经在 docker 容器中为 运行 设置了一个 Kippo 服务器。一切 运行 都很好,直到你杀死容器。终止容器(通过重启机器或通过 docker kill)使其无法用于 STDERR "Another twistd server is running, PID 1"。我怎么解决这个问题?我没有重置容器文件系统或类似东西的问题,因为我想要的一切都记录到数据库中。非常感谢
听起来你在容器中的 pid1 在被告知停止时没有正确清理它自己。这可能意味着它不会删除其 pid 文件,因此当您再次启动容器时它拒绝启动。
处理这个问题的一种方法可能是引入类似 supervisord 的东西,它可以处理接收停止信号,然后优雅地关闭 kippo 服务器。
另一种解决方案可能是以只读模式简单地启动容器。在只读模式下,容器没有写入层,根文件系统只是只读的。但是,如果 Kippo 无法创建 pid 文件,它可能会拒绝启动。 (参见 docker run --read-only
)
另一个解决方案是设置一个 ENTRYPOINT 脚本,在调用 kippo 上的 exec 之前删除 pidfile。
在 Docker 内,每个容器都在自己的 PID 命名空间中运行。这意味着由 dockerfile 启动的进程将始终是 PID 1,PID 将从那里向上计数。
twistd
期望 PID 具有足够的不确定性,它可以通过简单地比较 PID 是否相同来检查另一个 twistd
是否是 "already running"。因为,在 Docker 中,PID 永远是 1,所以这个检查总是成功的,而 twistd
认为它不应该启动。如果容器不干净地退出,twistd
将没有机会清理其 .pid
文件,并且状态将保留在容器的文件系统中。
由于 Docker 守护进程将命名容器并阻止两个匹配的 twistd
进程同时启动,因此 .pid
文件及其相关检查实际上没有用根本没有,所以你应该禁用它。您可以通过更改命令行以在插件名称前包含 --pidfile=
选项(正是这样,“=
”之后没有任何内容)来禁用它。我不熟悉 Kippo,但对于 twistd web
这将是 twistd --pidfile= web
。
希望对您有所帮助!
我已经在 docker 容器中为 运行 设置了一个 Kippo 服务器。一切 运行 都很好,直到你杀死容器。终止容器(通过重启机器或通过 docker kill)使其无法用于 STDERR "Another twistd server is running, PID 1"。我怎么解决这个问题?我没有重置容器文件系统或类似东西的问题,因为我想要的一切都记录到数据库中。非常感谢
听起来你在容器中的 pid1 在被告知停止时没有正确清理它自己。这可能意味着它不会删除其 pid 文件,因此当您再次启动容器时它拒绝启动。
处理这个问题的一种方法可能是引入类似 supervisord 的东西,它可以处理接收停止信号,然后优雅地关闭 kippo 服务器。
另一种解决方案可能是以只读模式简单地启动容器。在只读模式下,容器没有写入层,根文件系统只是只读的。但是,如果 Kippo 无法创建 pid 文件,它可能会拒绝启动。 (参见 docker run --read-only
)
另一个解决方案是设置一个 ENTRYPOINT 脚本,在调用 kippo 上的 exec 之前删除 pidfile。
在 Docker 内,每个容器都在自己的 PID 命名空间中运行。这意味着由 dockerfile 启动的进程将始终是 PID 1,PID 将从那里向上计数。
twistd
期望 PID 具有足够的不确定性,它可以通过简单地比较 PID 是否相同来检查另一个 twistd
是否是 "already running"。因为,在 Docker 中,PID 永远是 1,所以这个检查总是成功的,而 twistd
认为它不应该启动。如果容器不干净地退出,twistd
将没有机会清理其 .pid
文件,并且状态将保留在容器的文件系统中。
由于 Docker 守护进程将命名容器并阻止两个匹配的 twistd
进程同时启动,因此 .pid
文件及其相关检查实际上没有用根本没有,所以你应该禁用它。您可以通过更改命令行以在插件名称前包含 --pidfile=
选项(正是这样,“=
”之后没有任何内容)来禁用它。我不熟悉 Kippo,但对于 twistd web
这将是 twistd --pidfile= web
。
希望对您有所帮助!