【问题标题】:Docker - capturing logs when replacing PID 1Docker - 替换 PID 1 时捕获日志
【发布时间】:2018-09-22 08:57:17
【问题描述】:

我一直在互联网上积极寻找有关此的信息,但这似乎是一个特殊的用例。

我正在尝试在 Kubernetes/Openshift 集群中部署一个运行旧后端的 docker 容器。

容器使用 entrypoint.sh 脚本启动,该脚本将在启动之前初始化后端所需的依赖项。

我希望后端为 PID 1 - 以便使用 docker/openshift 捕获后端日志。

为此,我在 entrypoint.sh 脚本的末尾有一个 exec 命令,它启动我的后端,从而用我的后端替换了 entrypoint.sh 进程(由 docker 分配了 PID 1)。

问题:

在 entrypoint.sh 中执行 exec 时,docker 停止捕获日志,因此在执行“docker logs $MY_CONTAINER_ID”时,我的后端进程没有任何日志被 docker 捕获。

进入容器后,我确实看到一切正常:

我的后端进程以 PID 1 运行,进程文件描述符 1/2 正确设置,捕获我的后端进程的 STDOUT 和 STDERR。

有谁知道这是否是缺少配置问题?或者考虑到我用 exec 替换 PID 1,docker 是否只是设计成这样工作?

【问题讨论】:

    标签: docker kubernetes openshift dockerfile


    【解决方案1】:

    我看不出你所描述的有什么问题。进程 ID 1 的 stdout/stderr 应该被捕获,任何子进程如果继承父进程(进程 ID 1)的 stdout/stderr 也会被捕获。

    如果应用程序设置为记录到普通文件并且不使用 stdout/stderr,您可能会遇到问题。在这些情况下,如果他们只接受一个文件,请使用/proc/1/fd/1 作为日志文件路径。这将导致日志消息通过进程 ID 1 的 stdout 输出。

    请注意,如果您的应用程序使用的日志框架想要在您给它的路径上进行自己的日志文件轮换,您需要禁用它,您希望它继续使用相同的文件路径而不是尝试重命名或截断它。

    【讨论】:

    • 非常感谢您的回答!您的回答昨天在我脑海中引发了一个想法,我弄清楚了问题所在。我将在下面的回答中详细说明这个问题。
    【解决方案2】:

    我发现了问题:

    后端实际上设置为在 STDOUT 和 STDERR 之间创建符号链接以记录容器本身中的文件。例如:应用程序代码记录在 STDOUT 上,后端启动脚本将 STDOUT 重定向到日志文件(旧版应用程序...)。

    docker 容器在执行入口点时本机使用管道进程来处理 STDOUT 和 STDERR。

    问题:

    当后端进程最后替换 entrypoint.sh 进程时,STDOUT 和 STDERR 符号链接会发生变化 - 如上所述,我猜这会影响 docker 守护进程并阻止 docker 收集任何进一步的登录标准输出和标准错误。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2021-08-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-02-24
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多