Systemd убил мой сервис vetcore: “Успешно деактивировано”

Вопрос или проблема

Я создал файл systemd для моего bash-скрипта на .NET Core в Linux. Но когда я запускаю файл службы, systemd постоянно завершает его с результатом “служба: успешно деактивирована.”

Я пытался вставить Type=forking или Type=oneshot, но ни один из вариантов не сработал. Что мне делать?

Вот файл службы:

[Unit]
Description=Пример приложения .NET Web API, работающего на Ubuntu

[Service]
Type=oneshot
ExecStart=/usr/bin/updatem
User=root

[Install]
WantedBy=multi-user.target

Вот результат:

10:57 AM    kill UpdateM
10:57 AM    запуск UpdateM
10:57 AM    3
10:57 AM    2
10:57 AM    1
10:57 AM    UpdateM (v.1.0.0.12)
10:57 AM    UpdateM (v.1.0.0.12) запущен.
10:57 AM    Запуск
10:57 AM    updatem.service: успешно деактивирована.
10:57 AM    Завершено. Пример приложения .NET Web API, работающего на Ubuntu.

С Type=oneshot вам часто также потребуется RemainAfterExit=yes, чтобы systemd считал службу “работающей” после завершения процесса, вызванного строкой ExecStart=.

Из man systemd.service о Type=oneshot:

Обратите внимание, что если этот параметр используется без RemainAfterExit=, служба никогда не войдет в состояние “активного” юнита, а сразу перейдет из состояния “активации” в “деактивацию” или “мертва”, так как не настроен процесс, который должен работать непрерывно. В частности, это означает, что после выполнения службы такого типа (и которая не имеет установленного RemainAfterExit=) она не будет показана как запущенная впоследствии, а как мертвая.

Таким образом, поведение, которое вы наблюдаете, именно то, что ожидается с Type=oneshot + без RemainAfterExit=yes.

Если ваш скрипт /usr/bin/updatem фактически создает дочерний процесс, который должен продолжать работу, то Type=forking будет правильным выбором типа службы.

Но если скрипт /usr/bin/updatem просто отправляет команду другому уже существующему процессу, вызывая его для запуска чего-то еще, и скрипт вместе со всеми его прямыми потомками завершится, как только команда будет отправлена, то Type=oneshot, вероятно, с RemainAfterExit=yes, будет правильным выбором.

Вы также можете добавить строку ExecStop=, указывающую на другой скрипт, который отправит другую команду для остановки процесса, запущенного скриптом /usr/bin/updatem, если это необходимо. Это позволит systemctl stop UpdateM.service также быть значимой операцией и сделает так, что systemd остановит ваш процесс более корректно во время завершения работы системы, если он все еще работает.

Если вы измените файл службы без использования systemctl edit, не забудьте запустить systemctl daemon-reload, чтобы изменения в файле службы вступили в силу.

Ответ или решение

Конечно! Вот полный ответ на ваш вопрос относительно того, почему ваш сервис с .NET (в данном случае, скрипт updatem) завершает свою работу с сообщением "Deactivated successfully" и что можно сделать, чтобы это исправить.

Проблема

Вы наблюдаете следующую ситуацию: когда вы запускаете свой сервис, он завершает выполнение моментально, и systemd сообщает, что сервис "успешно деактивирован". Это поведение ожидаемо для сервиса, определенного с типом Type=oneshot, так как он сразу же завершает свою работу после выполнения команды.

Решение

Вам нужно выбрать правильный тип сервиса и возможно добавить некоторые дополнительные параметры, чтобы управлять поведением вашего скрипта.

  1. Тип сервиса:

    • Если ваш скрипт updatem создает дочерний процесс, который должен продолжать работать, вам следует использовать Type=forking. Это позволяет systemd отслеживать родительский процесс, который вы создали, и считать сервис работающим до тех пор, пока процесс не завершится.
    • Если ваш скрипт просто инициирует другую задачу (например, отправляет команду на старт другого приложения) и сам по себе завершается, то вам следует использовать Type=oneshot, но с добавлением параметра RemainAfterExit=yes.
  2. Пример конфигурации сервиса:

Вот как может выглядеть ваша служебная конфигурация для обоих случаев:

Вариант 1: Use Type=forking

[Unit]
Description=Example .NET Web API App running on Ubuntu

[Service]
Type=forking
ExecStart=/usr/bin/updatem
User=root

[Install]
WantedBy=multi-user.target

Вариант 2: Use Type=oneshot with RemainAfterExit=yes

[Unit]
Description=Example .NET Web API App running on Ubuntu

[Service]
Type=oneshot
RemainAfterExit=yes
ExecStart=/usr/bin/updatem
User=root

[Install]
WantedBy=multi-user.target

Дополнительные настройки

  • ExecStop: Вы также можете добавить строку ExecStop=, которая укажет команду для остановки сервиса, если это необходимо. Это позволит вашему сервису быть корректно остановленным через systemctl stop UpdateM.service.

Перезагрузка конфигурации

После внесения изменений в файл сервиса не забудьте выполнить команду systemctl daemon-reload, чтобы применить изменения в конфигурации.

Заключение

С учетом вышеизложенного, правильный выбор типа сервиса и использование параметра RemainAfterExit=yes помогут вам успешно управлять вашим сервисом и избежать нежелательной деактивации. Проверяйте логи journalctl -u UpdateM.service для получения дополнительной информации о состоянии вашего сервиса в случае возникновения проблем.

Оцените материал
Добавить комментарий

Капча загружается...