这回答命令行命令自动杀死一个命令后,一定的时间
建议使用1行方法使bash命令行中运行的命令超时:
( /path/to/slow command with options ) & sleep 5 ; kill $!
但是,给定的“长时间运行”命令可能会在超时之前完成。
(让我们称它为“通常运行时间长但有时很快”的命令,或者简称为tlrbsf。)
所以这个漂亮的一行方法有几个问题。
首先,睡眠不是有条件的,因此在序列完成所花费的时间上设置了一个不希望的下界。当tlrbsf命令在2秒内完成时,考虑30秒或2m甚至5m的睡眠时间——这是非常不可取的。
其次,kill是无条件的,因此该序列将尝试kill一个未运行的进程并抱怨它。
所以…
是否有一种方法可以超时一个典型的长时间运行但有时快速(“tlrbsf”)命令
有一个bash实现(另一个问题已经有Perl和C的答案)
将终止在较早的两个:TLRBSF程序终止,或超时过去
不会杀死不存在/不运行的进程(或者,可选:不会抱怨失败的杀死)
不一定非要是一行字
可以在Cygwin或Linux下运行吗
... 还有,为了加分
在前台运行TLRBSF命令
任何“睡眠”或额外的进程在后台
这样,TLRBSF命令的stdin/stdout/stderr可以重定向,就像它已经直接运行吗?
如果是,请分享你的代码。如果不是,请解释原因。
我花了一段时间试图破解前面提到的例子,但我的bash技能达到了极限。
使用实例在1秒后使slows命令超时。
timeout 1 || echo "I failed, maybe due to timeout "
要确定命令是否超时或由于自身原因失败,请检查状态代码是否为124:
# ping the address 8.8.8.8 for 3 seconds, but timeout after only 1 second
timeout 1 ping 8.8.8.8 -w3
EXIT_STATUS=$?
if [ $EXIT_STATUS -eq 124 ]
then
echo 'Process Timed Out!'
else
echo 'Process did not timeout. Something else went wrong.'
fi
exit $EXIT_STATUS
注意,当退出状态为124时,您不知道它是由于您的timeout命令而超时,还是命令本身由于它自己的一些内部超时逻辑而终止,然后返回124。不过,在这两种情况下,您都可以安全地假设发生了某种超时。
我提出了一个问题,以保留shell上下文和允许超时,唯一的问题是它将停止脚本执行超时-但这是我提出的需求很好:
#!/usr/bin/env bash
safe_kill()
{
ps aux | grep -v grep | grep $1 >/dev/null && kill ${2:-} $1
}
my_timeout()
{
typeset _my_timeout _waiter_pid _return
_my_timeout=$1
echo "Timeout($_my_timeout) running: $*"
shift
(
trap "return 0" USR1
sleep $_my_timeout
echo "Timeout($_my_timeout) reached for: $*"
safe_kill $$
) &
_waiter_pid=$!
"$@" || _return=$?
safe_kill $_waiter_pid -USR1
echo "Timeout($_my_timeout) ran: $*"
return ${_return:-0}
}
my_timeout 3 cd scripts
my_timeout 3 pwd
my_timeout 3 true && echo true || echo false
my_timeout 3 false && echo true || echo false
my_timeout 3 sleep 10
my_timeout 3 pwd
输出:
Timeout(3) running: 3 cd scripts
Timeout(3) ran: cd scripts
Timeout(3) running: 3 pwd
/home/mpapis/projects/rvm/rvm/scripts
Timeout(3) ran: pwd
Timeout(3) running: 3 true
Timeout(3) ran: true
true
Timeout(3) running: 3 false
Timeout(3) ran: false
false
Timeout(3) running: 3 sleep 10
Timeout(3) reached for: sleep 10
Terminated
当然,我认为有一个目录叫做脚本