我有一个跟踪进程的脚本,如果该进程终止,它将重新生成它。我希望跟踪脚本也可以通过为跟踪脚本提供一个sigterm(例如。)来告知进程。换句话说,如果我杀死跟踪脚本,它也应该杀死它跟踪的进程,而不是再生成并退出。
将几个帖子(我认为是最佳做法,例如不使用PID文件)拼凑在一起,我得到以下内容:
#!/bin/bash
DESC="Foo Manager"
EXEC="python /myPath/bin/FooManager.pyc"
trap "BREAK=1;pkill -HUP -P $BASHPID;exit 0" SIGHUP SIGINT SIGTERM
until $EXEC
do
echo "Server $DESC crashed with exit code $?. Restarting..." >&2
((BREAK!=0)) && echo "Breaking" && exit 1
sleep 1
done
所以,现在如果我在一个xterm中运行这个脚本。然后在另一个xterm中我发送类似的脚本:
kill -HUP <tracking_script_pid> # Doesn't work.
kill -TERM <tracking_script_pid> #Doesn't work.
跟踪脚本没有结束或任何事情。如果我从命令行运行FooManager.pyc,它将在SIGHUP和SIGTERM上死亡。无论如何,我在这里可能做错了什么,也许还有不同的方法可以做到这一点?
感谢。
答案 0 :(得分:3)
从手册:
如果Bash正在等待命令完成并收到已设置陷阱的信号,在命令完成之前不会执行陷阱。当Bash等待异步命令时通过
wait
内置,接收已设置陷阱的信号将导致wait
内置函数立即返回,退出状态大于128,之后立即执行陷阱。 / p>
强调是我的。
所以在你的情况下,当你的命令正在执行时,Bash会等到它结束才会触发陷阱。
要解决此问题,您需要将程序作为作业运行,并等待它。如果您的程序永远不会以大于128的返回码退出,您可以简化以下代码,但我没有做出这样的假设:
#!/bin/bash
desc="Foo Manager"
to_exec=( python "/myPath/bin/FooManager.pyc" )
trap 'trap_triggered=true' SIGHUP SIGINT SIGTERM
trap_triggered=false
while ! $trap_triggered; do
"${to_exec[@]}" &
job_pid=$!
wait $job_pid
job_ret=$?
if [[ $job_ret = 0 ]]; then
echo >&2 "Job ended gracefully with no errors... quitting..."
break
elif ! $trap_triggered; then
echo >&2 "Server $desc crashed with exit code $job_ret. Restarting..."
else
printf >&2 "Received fatal signal... "
if kill -0 $job_pid >&/dev/null; then
printf >&2 "killing job $job_pid... "
kill $job_pid
wait $job_pid
fi
printf >&2 "quitting...\n"
fi
done
备注强>