发送SIGTERM到所有进程

我有一个bash脚本调用run.sh启动多个进程

 #!/bin/bash proc1 & proc2 & proc3 & final # this runs until sigterm 

当我执行run.sh并发送一个SIGTERM到run.sh,我不认为SIGTERM被发送到final ,我不认为它被发送到proc1proc2proc3 。 请注意,在这个用例中,这是一个运行run.sh的docker容器,运行run.sh docker stop是我试图发送SIGTERM的方式。

bash脚本最简单的方法是将sigterm发送到所有启动的进程? 我能想到的唯一方法是用&开始final ,然后在run.sh做一个while循环?

编辑 – 我试过了,但似乎并没有工作:在run.sh

 #!/bin/bash _term() { echo "Caught SIGTERM signal!" } trap _term SIGTERM echo "hi" sleep 100000 & wait $! 

在运行docker站时,我从来没有看到Caught SIGTERM signal!

你说你在一个Docker容器中运行这个脚本。 你可以给我们更多关于你如何启动容器和run.sh被调用的细节吗?

docker stop被调用或容器接收到一个直接的SIGTERM ,包含PID 1的进程将收到它。 当您的run.sh创build在后台运行的subprocess时, 它也必须将信号转发给它们

因此,在& bash脚本中创build后台subprocess并不是一个好方法。 使用pipe理员将是一个很好的做法,因为它可以正确处理信号并将其转发到其subprocess,而无需进一步编写脚本。

另外, supervisord不应该作为shellsubprocess本身启动。 如果你在你的Dockerfile它指定为你的容器命令,会发生这种情况:

 CMD /usr/bin/supervisord 

相反,它应该是这样的:

 CMD ["/usr/bin/supervisord"] 

这样,pipe理员成为PID 1的根进程,并将正确接收所有信号并将其redirect到其subprocess。

使用jobs -p获得任何后台作业的进程ID,然后通过它们来kill

 trap 'kill $(jobs -p)' TERM proc1 & proc2 & proc3 & wait 

正确的,我会收集他们全​​部在一个数组,然后发送信号给他们每一个完成后。 我会用awk '{ system("kill -15 " $1)}'