docker-compose 不在 Python 应用程序中打印标准输出

Posted

技术标签:

【中文标题】docker-compose 不在 Python 应用程序中打印标准输出【英文标题】:docker-compose not printing stdout in Python app 【发布时间】:2018-12-24 00:34:54 【问题描述】:

在由 Docker Compose 管理的 Docker 容器内运行的 Python 应用程序中使用 print() 语句时,仅记录 sys.stderr 输出。没有看到香草print() 语句,所以这个:

print("Hello? Anyone there?")

...永远不会出现在常规日志中:

(您可以在我的应用中看到由其他库显式打印的其他日志,但没有我自己的调用。)

如何避免我的print() 呼叫被忽略?

【问题讨论】:

【参考方案1】:

默认情况下,Python 缓冲输出到sys.stdout

有几个选项:

1.调用明确的flush

重构原始打印语句以包含flush=True 关键字,例如:

print("Hello? Anyone there?", flush=True)

注意:这将导致 整个 缓冲区刷新,而不仅仅是相同的打印调用。因此,如果其他地方有“裸”打印函数调用(即没有 flush=True)没有明确无缓冲,这些也将始终被刷新。

您可以通过以下方式实现相同的目标:

import sys
sys.stdout.flush()

如果您想要最大程度地控制何时刷新将发生,则此选项很有用。

2。通过PYTHONUNBUFFERED env var 解除整个应用程序的缓冲

将以下内容放入您的docker-compose.yml 文件的environment 部分:

PYTHONUNBUFFERED: 1

这将导致stdout 的所有输出立即刷新。

3.使用-u运行python

与上面的选项 #2 一样,这将导致 Python 在应用程序的整个执行生命周期内“无缓冲”运行。只需使用 python -u <entrypoint.py> 运行 - 不需要环境变量。

【讨论】:

只有 flush=True 有效。 Windows 10、泊坞窗桌面、Python 3.7 @TDiddy - 当我写这篇文章时,它在 2018 年 7 月 16 日有效。我对未来不做任何保证。 在 docker 中运行一个应用程序给人的印象是应用程序没有运行......在查看其他服务器日志时,我们看到连接到来......所以问题主要是缓冲区......这是惊人的!谢谢! 对于第二种解决方案,似乎是 docker 更改了环境变量的语法。 ``` - PYTHONUNBUFFERED=1``` 为我工作【参考方案2】:

很简单,如果您在 Dockerfile 的行中添加选项 -u,它将打印您的日志:

CMD ["python", "-u", "my_python_script.py"]

无需更改环境变量或更改程序的所有打印语句。

【讨论】:

-y 是无效标志。 -u 是正确的(我会在上面的答案中添加它。) 不适用于 Python 3.7、windows 10、docker-desktop【参考方案3】:

使用pytest,我的解决方案是添加-s 选项。

例如,在我还需要详细模式的情况下,我必须输入pytest -sv

【讨论】:

以上是关于docker-compose 不在 Python 应用程序中打印标准输出的主要内容,如果未能解决你的问题,请参考以下文章

使用docker-compose部署极狐gitlab

使用docker-compose部署极狐gitlab

docker-compose 部署python项目

在docker-compose中运行python selenium

docker-compose进行部署容器的时候,报错权限不足

python测试开发django-180.docker-compose部署django+mysql环境