所以,基本上我是通过 docker 容器运行 cron 作业(python ETL 脚本)。这意味着,每天上午 12.30 我的 cron 作业都会运行
docker run $IMAGE
在 Dockerfile 中我有这样的脚本
# Run the script at container boot time.
CMD ["./run_manager.sh"]
这就是 ```run_manager.sh`` 的样子。
python3 main.py>>main.log 2>&1
我正在使用这样的python
logging
模块
#!/usr/bin/env python3
# encoding: utf-8
"""
This file contains the script
"""
import logging
from contextlib import AbstractContextManager
import polars as pl
import tensorflow as tf
import sqlalchemy as sa
logging.basicConfig(format='%(asctime)s|%(levelname)s: %(message)s',
datefmt='%H:%M:%S, %d-%b-%Y', level=logging.INFO)
...
# Other codes
由于容器是一个临时容器,每天都会在触发 cron 时创建和销毁,因此我无法访问日志。那么我们如何改变它才能使日志在容器外持久化、轮转和可见呢?有办法吗?
现在它作为 cron 在本地 Ubuntu 实例上运行。但我很快就会将其迁移到谷歌云调度程序,尽快保持设计完整。在这种情况下,基本上还有什么解决方案能够查看过去作业的日志吗?
在容器中,您通常不记录到文件。由于容器具有隔离的文件系统,因此提取日志文件可能很棘手。更常见的设置是将容器日志记录到标准输出。
根据您所显示的内容,
logging
模块已经记录到标准输出,因此您只需删除包装器脚本中的重定向即可。如果这是包装器脚本所做的唯一事情,那么您甚至不需要它;您可以完全删除包装脚本,然后就可以了
ENV PYTHONUNBUFFERED=1
CMD ["./main.py"]
在你的 Dockerfile 中。 (脚本已经有一个正确的“shebang”行,不需要在命令行中显式使用
python3
,您还需要确保主机系统上有 chmod +x main.py
将其标记为可执行文件。ENV
行使 Python 无法在内部捕获日志消息;另请参阅 为什么 Python 应用程序在分离的 docker 容器中运行时不打印任何内容?)
在您当前显示的表单中,
docker run
会将日志直接打印到其自己的标准输出。如果您的 cron 守护程序设置为通过电子邮件发送 cron 作业的结果,您将在电子邮件中收到日志。更一般地说,只要容器未被删除,您就可以使用 docker logs
检索这些日志。
在云环境中,这是从容器进程中获取日志的“正常”方式。例如,如果您在 Kubernetes 中运行此程序,您将使用
kubectl logs
而不是 docker logs
,但底层机制仍然相同。我希望如果您登录到标准输出而不是文件,任何能够运行容器和报告日志的东西都可以工作。