检查双进程执行是否真实



我创建了一个脚本来验证计划的进程是否已在运行,在这种情况下,我阻止执行显示消息"脚本已在运行"。问题是我插入了这些代码行

scriptToVerify="send_xxxx.sh ${1} ${2}";
num_proc=`ps auxww | grep "$scriptToVerify" | grep -v $$ | grep -v grep | awk /./ | /usr/bin/wc -l`;
if [ $num_proc -gt 1 ];
then
sl_log "---------------------------Warning---------------------------"
sl_log "$scriptToVerify Already running"
exit 0;
fi

在大量脚本中(每个脚本都计划,有时同时计划)。我尝试了不同的解决方案:使用 flock 指令,使用锁定文件,但每次(甚至是我上面写的指令)我的代码工作几周,然后开始报告"脚本已经在运行"也不是真的。

不幸的是,我无法管理调度程序,那么如何修改脚本以验证进程是否实际正在运行?

使用ps ... | grep ... | grep -v ... | grep -v grep | ...按其名称(或命令行)匹配进程充满了问题(例如$$匹配也是PID的一部分,如其中一个注释中所述),在这种情况下使用pgrep(1)应该容易得多,并为您提供所需的内容。

您也不必担心它的输出(即使它可以-c计数匹配项),而只需使用它会返回0如果匹配的内容1的事实。在这种情况下,请使用-f与完整的命令行匹配,而不仅仅是进程名称。

if pgrep -f "${scriptToVerify}" >/dev/null; then
echo "'${scriptToVerify}' already running"
fi

如果您仍然收到意外的不需要的匹配,您也可以使其更详细一些(注意:某些进程可能会在调用pgrep和随后的ps之间终止):

matched_pids=$(pgrep -f "${scriptToVerify}")
if [[ -n "${matched_pids}" ]]; then
echo "Already running:"
ps -o pid,cmd -p ${matched_pids}
fi

您还可以确保模式不会意外匹配不需要的字符串(进程),例如,如果scriptToVerify是完全匹配的,则使用pgrep -f "${scriptToVerify}$"而不是其他参数,甚至pgrep -f "^${scriptToVerify}$",或者pgrep -f "(^|\<)${scriptToVerify}$"以脚本 basename 开头的值和所有参数都应匹配。

最新更新