whileループはコマンドにパイプしますが、パイプされたコマンドが失敗した場合は別のコマンドを実行します。

whileループはコマンドにパイプしますが、パイプされたコマンドが失敗した場合は別のコマンドを実行します。

環境: armv7l GNU/Linux Debian Jessie, GNU bash,v4.3.30(1) - リリース(arm-unknown-linux-gnueabihf)

  • do_stuff: STDOUTで出力を生成する長期実行プロセス
  • compare_output.plperl出力に従って操作を実行するスクリプトです。

compare_output.plプロセスが中断(死)した場合は、再開できるようにしたいですcompare_output.pl。単純なループechoの後でもwhile(そしてその後も)compare_output.pl成功しませんでした。

残念ながら、プロセスに対してキャッシュ/バッファされた報酬をbash保存する方法がわかりません。do_stuff

while true;
do
  ...
  do_stuff (which generates lot of output linewise to STDOUT)
  ...
done | compare_output.pl 
#then something like this should happen, while retaining 
#the while loop and being able to "reattach" to the pipe.
"compare_output died? restart it "

時にはcompare_output.pl中断され(実際に終了し)、パイプライン入力全体が失われます。 (compare_output.pl壊れてはいけないことは言うまでもありませんが、それは別の日の別の質問です)。

中断したら、compare_outputパイプ出力に再接続できるようにwhileループを再利用できるようにしたいです。 1 つ以上の行が欠落していることは許可されます。

パイプの代わりにコマンド置換を試しました。

while true;
do
  ...
  do_stuff (which generates lot of output linewise)
  ...
done < <( compare_output.pl )
# then something like this should happen, while retaining
# the while loop and being able to "reattach" to the pipe.
compare_output died? restart it "

restart_while_loopcompare_output.pl失敗(死亡)した場合

読み取りと適用 Bash:「読み込み中」プロセス置換操作がパイプから抜け出すことはできません。

compare_output.pl出力を中断することに加えて、これは私が死んだ後に行動したい問題を解決しないようです。

私がこれをするときCTRL-Cその後、myがecho test実行されます。これは 。代わりに私が実行したものですcompare_output.pl restart test

それ以外の場合は、do_stuffまだ長い間実行されます。

それ以外にも、パイプラインとプロセスの置換について読んでみましたが、ここに質問が多いが、検索する適切なキーワードが不足しているようです。

わかりました シェルループを使用してテキストを処理するのはなぜ悪い習慣と見なされますか? そして私のやり方は悪い習慣ですが、今すぐは変えられない状況だという点をご理解ください。

それでは、死んだ後にできるだけ早く起こるようにするにはどうすればよいですかcompare_output.pl? (プロセスの実行が停止されており、psエントリはありません。)

これが実際に機能する唯一のオプションである場合は、ループを完全に書き直すことになります。今は他のスクリプト言語を使用したくありませんが、必要であれば(とにかく)書き換えることができますが、そうしたくありませperlん。

ベストアンサー1

最初のループを別のループにパイプします。

while :; do ./do_stuff ; done | 
  while :; do ./compare_output.pl ; done

おすすめ記事