EXIT
次のように、トラップを介して一種のクリーンアップコードを実行するシェルスクリプトがあるとします。
#!/bin/bash
mytrap () {
echo "It's a trap!" >&2
}
trap mytrap exit
echo I am at the end of the script.
期待どおりにIt's a trap!
スクリプトが終了すると、以下が印刷されます。
$ sh myscript
I am at the end of the script.
It's a trap!
次のように、最終的に他のコマンドにパイプされるいくつかの出力を生成する関数を追加するようにスクリプトを変更します。
#!/bin/bash
mytrap () {
echo "It's a trap!" >&2
}
myfunc () {
echo "I've got a bad feeling about this..."
}
trap mytrap exit
myfunc | cat > /dev/null
echo I am at the end of the script.
その中のコードはパイプのためにサブシェルで実行されますmyfunc
...そしてサブシェルは親シェルの動作を継承しないようですtrap
。つまり、ここでトラップコードでクリアする必要がある作業を実行しても起こりません。
だからこれを試してみてください:
myfunc () {
trap mytrap EXIT
echo "I've got a bad feeling about this..."
}
mytrap
そして、サブシェルが終了しても実行されません。次の明示的なものが必要であることがわかりましたexit
。
myfunc () {
trap mytrap EXIT
echo "I've got a bad feeling about this..."
exit
}
上記のコードを使用すると、mytrap
サブシェルを終了すると適切にトリガーされます。
$ sh myscript
It's a trap!
I am at the end of the script.
It's a trap!
これが予想される動作ですか?私はここでいくつかの事実に驚きました。
trap
設定はサブシェルに継承されません。EXIT
サブシェルの暗黙的なシャットダウンがトラップをトリガーしないようです。