Как я могу запустить команду ExecStartPost из файла единицы systemd, которая может закончиться или нет

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

Я пытаюсь написать файл unit для systemd. Когда я запускаю службу siad, я хочу запустить другую команду, /usr/sbin/clearshare-scheduler.sh, которая может выполняться в течение нескольких часов или завершиться немедленно. Я пробовал сделать это с помощью ExecStartPost, но systemd не одобряет, если команда не завершится в короткий срок и выдает сообщение об ошибке. Пример файла:

[Unit]
Description=Siad
After=syslog.target network.target

[Service]
Type=simple
OOMScoreAdjust=500
PIDFile=/var/run/siad.pid
EnvironmentFile=/etc/sysconfig/siad
Environment="SIA_DATA_DIR=/var/lib/siad-data"
ExecStart=/usr/bin/siad $EXTRA_ARGS
ExecStop=/usr/bin/siac stop
WorkingDirectory=/var/lib/sia/
ExecStartPost=/usr/bin/sh -c 'umask 022; /usr/bin/pgrep siad > /var/run/siad.pid'
ExecStartPost=/usr/sbin/clearshare-scheduler.sh

[Install]
WantedBy=multi-user.target

Я пробовал запускать его с помощью “&”, чтобы поместить в фоновый режим, и с помощью nohup, но это тоже не сработало.

Попробуйте добавить TimeoutStartSec= под [Service]. Это влияет на все процедуры запуска.

https://www.freedesktop.org/software/systemd/man/systemd.service.html#TimeoutStartSec=

Просто добавьте команду /usr/sbin/clearshare-scheduler.sh как вторую службу, так как она требует от вашей первой службы. Надеюсь, это поможет!

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

Для того чтобы корректно запускать команду clearshare-scheduler.sh в файле единицы systemd, которая может выполняться долго или завершаться сразу, необходимо учитывать несколько важных аспектов. Ваша текущая реализация с использованием ExecStartPost может привести к неудачам, если выполняемая команда не завершится в течение заданного времени. В этом ответе я предложу подход, который позволит избежать этих проблем.

Решение проблемы

Подход 1: Использование ExecStart с фоновым запуском

Одним из решений данной проблемы является запуск вашей команды с помощью ExecStart, добавляя к ней & для выполнения в фоновом режиме. Однако учтите, что для повышения устойчивости и контроля над процессом, можно обернуть команду в скрипт.

  1. Создание вспомогательного скрипта:

    Создайте скрипт, который будет запускать вашу команду в фоне и завершать выполнение, не дожидаясь её завершения. Например, создайте файл /usr/local/bin/start-clearshare-scheduler.sh с содержимым:

    #!/bin/bash
    /usr/sbin/clearshare-scheduler.sh &

    Не забудьте сделать его исполняемым:

    chmod +x /usr/local/bin/start-clearshare-scheduler.sh
  2. Обновление файла единицы systemd:

    Теперь вы можете изменить ваш unit-файл следующим образом:

    [Unit]
    Description=Siad
    After=syslog.target network.target
    
    [Service]
    Type=simple
    OOMScoreAdjust=500
    PIDFile=/var/run/siad.pid
    EnvironmentFile=/etc/sysconfig/siad
    Environment="SIA_DATA_DIR=/var/lib/siad-data"
    ExecStart=/usr/bin/siad $EXTRA_ARGS
    ExecStop=/usr/bin/siac stop
    WorkingDirectory=/var/lib/sia/
    ExecStartPost=/usr/bin/sh -c 'umask 022; /usr/bin/pgrep siad > /var/run/siad.pid'
    ExecStartPost=/usr/local/bin/start-clearshare-scheduler.sh
    
    [Install]
    WantedBy=multi-user.target

Подход 2: Создание отдельной службы для clearshare-scheduler.sh

Если clearshare-scheduler.sh имеет свои зависимости и его стоит отслеживать отдельно, вы можете создать для него отдельный unit-файл:

  1. Создание нового unit-файла:

    Создайте файл, например, /etc/systemd/system/clearshare-scheduler.service:

    [Unit]
    Description=Clearshare Scheduler
    After=siad.service
    
    [Service]
    Type=simple
    ExecStart=/usr/sbin/clearshare-scheduler.sh
    
    [Install]
    WantedBy=multi-user.target
  2. Обновление основного unit-файла:

    Теперь просто измените ваш первоначальный unit-файл, убрав команду для clearshare-scheduler.sh:

    [Unit]
    Description=Siad
    After=syslog.target network.target
    
    [Service]
    Type=simple
    OOMScoreAdjust=500
    PIDFile=/var/run/siad.pid
    EnvironmentFile=/etc/sysconfig/siad
    Environment="SIA_DATA_DIR=/var/lib/siad-data"
    ExecStart=/usr/bin/siad $EXTRA_ARGS
    ExecStop=/usr/bin/siac stop
    WorkingDirectory=/var/lib/sia/
    ExecStartPost=/usr/bin/sh -c 'umask 022; /usr/bin/pgrep siad > /var/run/siad.pid'
    
    [Install]
    WantedBy=multi-user.target
  3. Запуск и активация службы:

    Чтобы активировать и запустить новую службу, выполните следующие команды:

    systemctl daemon-reload
    systemctl enable clearshare-scheduler.service

Заключение

Оба предложения обеспечивают то, что команда clearshare-scheduler.sh может выполняться долго, не вызывая сбоев в вашем основном сервисе siad. Выбор между первым и вторым подходом зависит от вашей архитектуры. Первый подойдет для простоты, второй — для большей модульности и отслеживания состояния.

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

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