In meiner Node-App binde ich auf das SIGINT
-Signal, um sanft zu stoppen (mit pm2
, aber das ist hier nicht relevant).
Meine App leitet auch ein paar untergeordnete Prozesse.
Ich bin in der Lage, SIGINT
anzuhängen, um sie abzufangen und anmutige Stopps auszuführen, jedoch werden meine untergeordneten Prozesse durch dasselbe Signal geleitet und daher sofort getötet.
Wie kann ich das Signal SIGINT
auf meinen untergeordneten Prozessen abfangen?
Ein Beispiel von dem, was ich mache:
%Vor% Standardmäßig haben untergeordnete Prozesse, die von child_process.spawn()
erstellt wurden, die gleiche Prozessgruppe als übergeordnetes Element, sofern sie nicht aufgerufen wurden mit der Option {detached:true}
.
Im Endeffekt verhält sich dieses Skript in verschiedenen Umgebungen anders:
%Vor%Bei interaktiven Shells wird standardmäßig ein SIGINT von Ctl-C an die gesamte Gruppe gesendet, so dass das nicht-untergeordnete Kind das SIGINT und exit:
bekommt %Vor% ... aber Aufrufe von kill(2)
können Ihren Elternprozess signalisieren, damit Kinder am Leben bleiben:
Allerdings ist pm2 ein ganz anderes Tier. Selbst wenn Sie die oben genannten Techniken ausprobieren, wird der gesamte Prozessbaum, einschließlich Ihres abgetrennten Prozesses, sogar mit einem langen --kill-timeout
:
Das scheint ein Fehler in PM2 zu sein.
Ich habe ähnliche Probleme durch Verwendung des init-Systems (systemd in meinem Fall) anstelle von pm2 bekommen, da dies eine bessere Kontrolle über die Signalverarbeitung ermöglicht.
Auf Systemd werden Signale standardmäßig an die gesamte Gruppe gesendet, aber Sie können KillMode=mixed
verwenden, um das Signal nur an den übergeordneten Prozess zu senden, aber noch an untergeordnete SIGKILL-Prozesse, wenn sie über das Zeitlimit hinaus ausgeführt werden.
Meine Systemdateien sehen wie folgt aus:
%Vor%Normalerweise löst man in C dies, indem man das Signal im Kind ignoriert (oder indem man es in einer neuen Prozessgruppe erzeugt, so dass das vom Terminal erzeugte Signal für die Vordergrundprozessgruppe es nicht erreicht).
>Aus dem Blick auf Ссылка sieht es nicht so aus, als ob NodeJs dafür eine API offen legt hat eine Option, um den Child-Prozess durch die Shell zu erzeugen, also kannst du es aktivieren und das Signal in der Shell ignorieren, was dazu führt, dass sein ignorierter Status an die untergeordneten Elemente der Shell vererbt wird.
%Vor%Wenn Sie nun Strg-C drücken, wird der Node-Prozess bearbeitet und der Schlafprozess wird fortgesetzt. (Falls Sie mit den anderen vom Terminal generierten Signalen nicht vertraut sind, können Sie diese Gruppe einfach durch Drücken von Ctrl- \ (sendet SIGQUIT an die Gruppe) abbrechen, wenn Sie den Coredump nicht stören).
Tags und Links node.js signals child-process