systemd 标准输出到文件并写入日志?

systemd 标准输出到文件并写入日志?

我经常做一个长期运行(约 5 天)的数据处理程序。我使用 Ubuntu 并通过 systemd 临时任务运行命令systemd-run --unit data_import /path/to/my-script.sh。它运行良好。我可以使用 查看脚本的日志标准输出journalctl -u data_import.service

我希望脚本中的 stdout(和 stderr)能保存到文件以及 systemd 日志中。我知道这systemd-run --unit data_import -p "StandardOutput=file:/path/my-logging-file.txt …会将 stdout 保存到该文件中。但是它不会记录到 journald 中。我尝试提供两次参数systemd-run -p "StandardOutput=file:/path/my-logging-file.txt" -p "StandardOutput=journal" …,但没有成功。

是否可以使用 systemd 将 stdout 记录到文件中到 systemd 日志?(对于 stderr 也一样?)

Ubuntu 18.04 & 20.04,systemd v250. 或 v245 等

答案1

我想我们不能,但找到了一个参考https://www.freedesktop.org/software/systemd/man/systemd.exec.html#StandardOutput=这可能会有所帮助(注意采取其中之一细绳)。

控制执行进程的文件描述符 1 (stdout) 连接到哪里。采取其中之一继承、null、tty、journal、kmsg、journal+console、kmsg+console、file:path、append:path、truncate:path、socket 或 fd:name。

虽然我们可以改变默认的标准输出类型。

答案2

您是否尝试过直接在脚本中创建日志文件并在每次需要时添加信息?我知道这很明显,但我很好奇它是否有效。

例如使用 bash,直接在脚本中:

# Declaration
LOG=/var/log/your_script_log.log
# Or with a date 
TODAY=$(date +%Y-%m-%d)
LOG=/var/log/your_script_log-$(TODAY).log
...
# Beginning of main script
echo -e $TODAY > $LOG
...
# Every time needed during the script
if [[ $state == *"stopped"* ]];then
    echo "A very important message." >> $LOG
...

使用这样的系统,您将需要配置 logrotate 以避免几个月后产生数百条日志。

答案3

@Amandasaurus 好的,我明白了。那么我建议您在“/etc/systemd/system/[脚本名称].service”下创建一个服务文件,并添加最少的必要信息:

[Unit]
Description=*The name of your script*

[Service]
ExecStart=/path/to/my-script.sh
ExecStop=/bin/kill $MAINPID
KillMode=process
Type=simple
StandardOutput=/path_to_log/service.log
StandardError=/path_to_log/service_error.log

[Install]
WantedBy=multi-user.target

然后配置一个 logrotate 或将“append”添加到 StandardOutput 参数。之后执行以下操作:

systemctl daemon-reload
systemctl start *The name of your service*

要启用服务启动功能:

systemctl enable *The name of your service*

服务文件中日志参数的来源:这里

相关内容