Существует ли типичный способ передачи пароля в файл Systemd Unit?

10

Я хотел бы запустить сервис, используя системный файл systemd. Эта служба требует пароль для запуска. Я не хочу хранить пароль в виде открытого текста в файле модуля systemd, потому что он доступен для чтения всем. Я также не хочу предоставлять этот пароль в интерактивном режиме.

Если бы я писал для этого обычный сценарий, я бы сохранял учетные данные в файле, принадлежащем пользователю root с ограниченными разрешениями (400 или 600), а затем считывал файл как часть сценария. Есть ли какой-то конкретный способ для системного стиля, или я должен просто следовать тому же процессу, что и в обычном сценарии оболочки?

SauceCode
источник
Относящиеся - serverfault.com/questions/413397/...
ОДС

Ответы:

11

Здесь возможны два подхода в зависимости от ваших требований. Если вы не хотите запрашивать пароль при активации службы, используйте EnvironmentFileдирективу. От man systemd.exec:

Аналогичен Environment =, но считывает переменные среды из текстового файла. Текстовый файл должен содержать разделенные новой строкой присваивания переменных.

Если вы действительно хотите , чтобы запрос, вы бы использовать один из systemd-ask-passwordдиректив. От man systemd-ask-password:

systemd-ask-password может использоваться для запроса системного пароля или пароля от пользователя, используя сообщение с вопросом, указанное в командной строке. При запуске из TTY он запросит пароль у TTY и распечатает его на стандартный вывод. При запуске без TTY или с --no-tty будет использоваться общесистемный механизм запросов, который позволяет активным пользователям отвечать через несколько агентов.

jasonwryan
источник
2
Обратите внимание, что существуют недостатки в передаче паролей в переменных среды (даже если файл, в котором заданы переменные, защищен), поскольку обычно можно отслеживать переменные среды процессов, принадлежащих другим пользователям (например, использующим ps ajxewww), чтобы кто-то мог забрать его оттуда.
filbranden
Спасибо! EnvironmentFileзапись с абсолютным путем к файлу с 400 разрешениями работает хорошо.
Левибостян
@filbranden Вы не можете читать переменные окружения процессов, принадлежащих другим пользователям.
Вики
2

Существует третья альтернатива этому, а также 2 предложения @jasonwryan.

выдержка из ответа Майкла Хэмптона на ServerFault - Как установить переменную среды в сервисе systemd?

В настоящее время лучший способ сделать это - запустить systemctl edit myserviceфайл, который создаст для вас файл переопределения или позволит отредактировать существующий.

В обычных установках это создаст каталог /etc/systemd/system/myservice.service.d, а внутри этого каталога создаст файл, имя которого оканчивается .conf(обычно override.conf), и в этом файле вы можете добавить или переопределить любую часть устройства, поставляемую дистрибутивом.

Например, в файле /etc/systemd/system/myservice.service.d/myenv.conf:

[Service]
Environment="SECRET=pGNqduRFkB4K9C2vijOmUDa2kPtUhArN"
Environment="ANOTHER_SECRET=JP8YLOc2bsNlrGuD6LVTq7L36obpjzxd"

Также обратите внимание, что если каталог существует и пуст, ваш сервис будет отключен! Если вы не собираетесь помещать что-либо в каталог, убедитесь, что оно не существует.

SLM
источник
1

Я могу предложить дополнительную альтернативу, которая может удовлетворить ваши потребности, но для этого необходимо выполнить несколько предварительных условий:

  • Вам необходимо настроить системный модуль как пользовательский.
  • Вам необходимо настроить связку ключей Gnome, я рекомендую этот метод: https://wiki.archlinux.org/index.php/GNOME/Keyring#PAM_method

Следующие шаги следующие:

Используйте secret-toolот libsecretхранить пароль. Например:

$ secret-tool store --label=myProgram myService password
Password: <type it here>

Если ваш исполняемый файл поддерживает чтение пароля из переменной окружения, лучше:

[Service]
ExecStart=/usr/bin/sh -c 'env SECRET=$(secret-tool lookup myService password) /usr/bin/script'

Если ваш исполняемый файл принимает пароль в качестве аргумента, вы все равно можете использовать secret-toolтак:

[Service]
ExecStart=/usr/bin/sh -c '/usr/bin/script --secret=$(secret-tool lookup myService password)'

Внимание : пароль будет хорошо виден при запуске, systemctl --user status myUnit.serviceтак как он показывает аргумент как запускаемый из командной строки. Это означает, что это также будет видно для пользователей, работающих topили ps -aux.

Дорон Бехар
источник