Bash機能でゼロ以外の終了状態をキャプチャして処理する方法は?

Bash機能でゼロ以外の終了状態をキャプチャして処理する方法は?

次のような(無意味な)Bash関数があるとしましょう。

myfunc() {
    ls
    failfailfail
    uptime
}

私は次のように実行します:

myfunc || echo "Something is wrong."

私が望むのは、ls実行されなければならないので、動作せずfailfailfail(存在しないので)uptime実行されないことです。関数の戻り値はゼロではなく、エラーメッセージが表示されます。戻り値は、失敗したコマンドの正確な終了状態である必要はなく、単にゼロにしてはいけません。

実際に起こるのは、出力を取得してlsから「-bash:failfailfail:command not find」、そして「-bash:failfailfail:command not find」の出力を取得することですuptime。失敗したシャットダウン状態が悪いため、エラーメッセージは表示されません。

set -e関数内や呼び出し関数の範囲では有用な効果はありません。私が望む方法で動作させることができる唯一の方法は次のとおりです。

myfunc() {
    ls || return $?
    failfailfail || return $?
    uptime || return $?
}

しかし、これは非常に反復的で醜いようです。これをきれいにする他の方法はありませんか?

ベストアンサー1

でなければ、set -eスクリプトfailfailfail全体(または関数がサブシェルで実行されている場合はサブシェル)が終了します。

関数でシェルの状態を変更する必要がない場合は、サブシェルで実行できます。

myfunc() (
    set -e
    ls
    failfailfail
    uptime
)

Bashのもう一つの方法は次のとおりです。ERR 実装するreturn。ローカル設定にするには、古いトラップ値を復元する必要がありますが、これは少し面倒です。

myfunc() {
    local old_ERR_trap=$(trap -p ERR)
    if [[ -z $old_ERR_trap ]]; then old_ERR_trap="trap - ERR"; fi
    trap 'local ret=$?; eval "$old_ERR_trap"; return $ret' ERR
    ls
    failfailfail
    uptime
}

おすすめ記事