systemd - reinicia sem parar

4

Eu tenho um pequeno problema. Eu tenho um programa (vamos chamá-lo de mestre) que, internamente, inicia vários programas (client1, client2 e client3) e os desconecta.

Agora, quero que o programa principal permaneça sempre on-line, então escrevi um arquivo de serviço systemd assim:

[Unit]
Description=Run the master
Before=runlevel2.target runlevel3.target runlevel4.target runlevel5.target
After=remote-fs.target systemd-journald-dev-log.socket all.target

[Service]
Type=forking
Restart=always
TimeoutSec=5min
IgnoreSIGPIPE=no
KillMode=process
RemainAfterExit=no
SysVStartPriority=5
ExecStart=/home/user/start_master.sh start
ExecStop=/home/user/start_master.sh stop
PIDFile=/var/run/mymaster.pid

[Install]
WantedBy=multi-user.target

O script inicial é como este:

#! /bin/sh

PIDFILE=/var/run/mymaster.pid

do_start() {
    /home/user/master >/dev/null 2>&1 &
    echo $!
}

case "$1" in
    start)
        PID=$(do_start)
        if [ -z $PID ]; then
                echo "Failed starting master"
                exit 2
        else
                echo $PID > $PIDFILE
        fi
        ;;
    stop)
        killall master client1 client2 client3 2>/dev/null
        rm $PIDFILE
        ;;
    restart)
        killall master 2>/dev/null
        $0 start
        ;;
    *)
        echo "Usage: $0 start|stop|restart" >&2
        exit 3
        ;;
esac

Meu comportamento desejado é:

  • no início: basta iniciar o mestre (ele cuidará de iniciar os clientes)
  • na reinicialização (ou quando o mestre é desligado): elimine o programa mestre e reinicie-o (já que ele será anexado aos clientes anteriores)
  • on stop: elimina o programa mestre e todos os clientes

Agora, com essa configuração, tudo funciona bem: quando eu inicio o serviço, isso é o que eu vejo:

$ systemctl status master.service
● master.service - Run the master
   Loaded: loaded (/etc/systemd/system/master.service; enabled)
   Active: active (running) since Wed 2016-10-19 16:16:33 CEST; 5s ago
  Process: 4161 ExecStop=/home/user/start_master.sh stop (code=exited, status=0/SUCCESS)
  Process: 4198 ExecStart=/home/user/start_master.sh start (code=exited, status=0/SUCCESS)
 Main PID: 4200 (master)
   CGroup: /system.slice/master.service
           ├─4200 /home/user/master
           ├─4203 /home/user/client1
           ├─4205 /home/user/client2
           └─4209 /home/user/client3

Além disso, a parada é executada corretamente. MAS ... quando eu quiser reiniciá-lo (seja chamando restart ou matando manualmente o programa mestre) o systemd executa o ExecStop ao invés do comando restart, matando todos os clientes também.

Existe uma maneira de alcançar o que eu queria?

Atenciosamente

PS. Estou usando o Debian 8.6.0 x64

    
por frarugi87 19.10.2016 / 16:21

1 resposta

3

O systemd não possui uma noção de reinicialização que não seja apenas stop-if-running + start. Você pode usar ExecReload= e usar systemctl reload em vez de reiniciar, mas a pergunta é por que você precisa disso?

Por que você reinicia o master sem reiniciar os clientes? Aliás, o que o mestre realmente faz? Seu script inicial me leva a acreditar que você está tentando fazer a supervisão do processo novamente, o que eu aconselharia - o systemd pode fazer isso, então use-o.

Eu recomendaria que você tentasse descobrir como você pode iniciar os clientes via systemd.

Em qualquer caso, o seu script de início é completamente supérfluo. Ele usa arquivos PID e todos os tipos de coisas que são absolutamente desnecessários porque o systemd já pode fazer tudo isso. Eu sugiro removê-lo e, em vez disso, apenas usando "ExecStart = / home / user / master" no seu arquivo .service (se o mestre é necessário depois de tudo), em seguida, ajuste o tipo = de "bifurcação" para "simples". Remova o "ExecStop" e "PIDFile".

Eu recomendo link como leitura adicional.

    
por 18.11.2016 / 14:21

Tags