Как перенаправить вывод службы systemd в файл
Я пытаюсь перенаправить вывод службы systemd
в файл, но он не работает:
[Unit]
Description=customprocess
After=network.target
[Service]
Type=forking
ExecStart=/usr/local/bin/binary1 agent -config-dir /etc/sample.d/server
StandardOutput=/var/log1.log
StandardError=/var/log2.log
Restart=always
[Install]
WantedBy=multi-user.target
Пожалуйста, исправьте мой подход.
Ответы
Ответ 1
Я думаю, что есть более элегантный способ решения проблемы: отправьте stdout/stderr в syslog с идентификатором и дайте команду своему администратору syslog разделить вывод по имени программы.
Используйте следующие свойства в вашем файле systemd:
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=<your program identifier> # without any quote
Затем, если ваш дистрибутив использует rsyslog для управления системными журналами, создайте файл в /etc/rsyslog.d/<new_file>.conf
со следующим содержимым:
if $programname == '<your program identifier>' then /path/to/log/file.log
& stop
Теперь сделайте файл журнала доступным для записи с помощью syslog:
# ls -alth /var/log/syslog
-rw-r----- 1 syslog adm 439K Mar 5 19:35 /var/log/syslog
# chown syslog:adm /path/to/log/file.log
Перезапустите rsyslog (sudo systemctl restart rsyslog
) и наслаждайтесь! Ваша программа stdout/stderr по-прежнему будет доступна через journalctl (sudo journalctl -u <your program identifier>
), но они также будут доступны в выбранном вами файле.
Источник через archive.org
Ответ 2
Если у вас новый дистрибутив с более новой systemd
( systemd
version 236 или newer), вы можете установить значения StandardOutput
или StandardError
для file:YOUR_ABSPATH_FILENAME
.
Длинная история:
В более новых версиях systemd
существует относительно новая опция (запрос github с 2016 года ish и расширение слияния/закрытия 2017 ish), где вы можете установить значения StandardOutput
или StandardError
для file:YOUR_ABSPATH_FILENAME
. Параметр file:path
задокументирован на самой последней systemd.exec
man systemd.exec
.
Эта новая функция является относительно новой и поэтому недоступна для более старых дистрибутивов, таких как centos-7 (или любые центы до этого).
Ответ 3
Вы можете получить эту ошибку:
Failed to parse output specifier, ignoring: /var/log1.log
На странице systemd.exec(5)
man:
StandardOutput=
Элементы управления, в которых подключен файловый дескриптор 1 (STDOUT) запущенных процессов. Принимает один из inherit
, null
, tty
, journal
, syslog
, kmsg
, journal+console
, syslog+console
, kmsg+console
или socket
.
Справочная страница systemd.exec(5)
описывает другие параметры, связанные с протоколированием. См. Также справочные страницы systemd.service(5)
и systemd.unit(5)
.
Или, может быть, вы можете попробовать такие вещи (все в одной строке):
ExecStart=/bin/sh -c '/usr/local/bin/binary1 agent -config-dir /etc/sample.d/server 2>&1 > /var/log.log'
Ответ 4
Если по какой-то причине невозможно использовать rsyslog, это будет делать:
ExecStart=/bin/bash -ce "exec /usr/local/bin/binary1 agent -config-dir /etc/sample.d/server >> /var/log/agent.log 2>&1"
Ответ 5
Я бы предложил добавить файл stdout
и stderr
в сам файл service
systemd.
Как вы настроили это не должно нравиться:
StandardOutput=/var/log1.log
StandardError=/var/log2.log
Так должно быть:
StandardOutput=file:/var/log1.log
StandardError=file:/var/log2.log
Убедитесь, что вы уже создали каталог. Я думаю, он не поддерживает создание каталога.
Ответ 6
Предположим, что журналы уже помещены в stdout/stderr, а система systemd регистрируется в /var/log/syslog
journalctl -u unitxxx.service
Jun 30 13:51:46 host unitxxx[1437]: time="2018-06-30T11:51:46Z" level=info msg="127.0.0.1
Jun 30 15:02:15 host unitxxx[1437]: time="2018-06-30T13:02:15Z" level=info msg="127.0.0.1
Jun 30 15:33:02 host unitxxx[1437]: time="2018-06-30T13:33:02Z" level=info msg="127.0.0.1
Jun 30 15:56:31 host unitxxx[1437]: time="2018-06-30T13:56:31Z" level=info msg="127.0.0.1
Config rsyslog (служба регистрации системы)
# Create directory for log file
mkdir /var/log/unitxxx
# Then add config file /etc/rsyslog.d/unitxxx.conf
if $programname == 'unitxxx' then /var/log/unitxxx/unitxxx.log
& stop
Перезапустить rsyslog
systemctl restart rsyslog.service