シェル関数でタイムアウト
うーん,と新しいアルゴリズムを考えて,とりあえず,プロトタイプ実装する,ということを,ときどきします.その後は,たいてい,パラメータをいろいろ変えてみて,データを取得するのですが,プロトタイプなので,よく異常終了したり,もっと悪い場合は無限ループに入るのか,だんまりになったりします.週末にデータを取ろうと思っても,起動して数パターンのデータを取得したところでスタックして,そのまま週末のほとんどをムダにする,なんてことがよくあります.
そこで,一定時間内に応答が返ってこなかったら,強制終了するタイムアウト機能がほしい!ということで,そんなシェルスクリプト・コマンドはいくらでもあるだろう,と思っていたのですが,ほとんど見つかりません.
なので,自作してみました.使い方は,timeout 5 sleep 10とかすると,10秒スリープしようとするのですが,約5秒でタイムアウトして,プロセスがKILLされます.echo文は動作確認用なので,実際に利用する場合は,適当に削除してください.
timeout() { count_timeout=$1 shift 1; echo exec \'$@\' $@ & pid=$! count=0 while [ $count -lt $count_timeout ] do isalive=`ps -ef | grep $pid | grep -v grep | wc -l` if [ $isalive -eq 1 ]; then echo $pid is alive. count=`expr $count + 1` sleep 1 else echo $pid was disapeared. count=`expr $count_timeout` fi done isalive=`ps -ef | grep $pid | grep -v grep | wc -l` if [ $isAlive = 1 ]; then kill -kill $pid wait $pid echo $pid was terminated by a SIG$(kill -l $?) signal. fi } timeout 5 sleep 3 timeout 5 sleep 10
これでよし,と思ったら,netatalkのパッケージにtimeoutという,そのものズバリのコマンドが含まれているようです...
まぁ,netatalkのパッケージがどこにでもインストールされているわけではないし,timeoutのためだけに,netatalkをインストールするのも問題がある(かもしれない)ので,それなりに利用価値は残っていることにしておきます.