apt-get update終了ステータス


8

のステータスをどのように確認しますapt-get updateか?

$ apt-get update ; echo "status is: $?"

Err http://security.debian.org stable/updates Release.gpg
Could not resolve 'security.debian.org'
Hit http://192.168.1.100 stable Release.gpg
Hit http://192.168.1.100 stable Release
Hit http://192.168.1.100 stable/main i386 Packages
Hit http://192.168.1.100 stable/contrib i386 Packages
Hit http://192.168.1.100 stable/non-free i386 Packages
Ign http://192.168.1.100 stable/contrib Translation-en
Ign http://192.168.1.100 stable/main Translation-en
Ign http://192.168.1.100 stable/non-free Translation-en
Reading package lists... Done
W: Failed to fetch http://security.debian.org/dists/stable/updates/Release.gpg  Could not resolve 'security.debian.org'
W: Some index files failed to download. They have been ignored, or old ones used instead.

status is: 0

ここにセキュリティ更新のフェッチでエラーがありますが、終了ステータスは0です

私の目標は、apt-get updateが正しく実行されるかどうかを確認するスクリプトです。

回答:


6

あなたの例でapt-get updateは、問題は致命的に悪いものではなく警告であると見なされていたため、エラーで終了しませんでした。本当に致命的なエラーがある場合は、ゼロ以外のステータスで終了します。

異常を認識する1つの方法は、でこれらのパターンをチェックすることですstderr

  • で始まる行W:は警告です
  • で始まる行E:はエラーです

上記のパターンが一致する場合、またはapt-get updateそれ自体の終了コードがゼロ以外の場合、次のようなものを使用して失敗をエミュレートできます。

if ! { sudo apt-get update 2>&1 || echo E: update failed; } | grep -q '^[WE]:'; then
    echo success
else
    echo failure
fi

注意!してif。これgrepは、パターンが一致した場合、つまりエラーが発生した場合に、exitが成功して終了するためです。エラーがない場合、grepそれ自体は失敗します。したがって、if条件はの終了コードを無効にすることgrepです。


1

apt-getのout / errが食べられないようにしたい場合(たとえば、ログファイルに書き込む場合)、これはより簡単な代替策になる可能性があります。

sudo apt-get update 2>&1 | tee /tmp/apt.err && ! grep -q '^[WE]' /tmp/apt.err

これが後で削除するために新しいファイルを残さないのはいいことですが、たとえば、grepをtee出力に置き換えると、終了コードを取得するのが難しくなるようです。


1

私は同じ問題に直面していた、と私はに依存している別の解決策を提案したいと思いますtee(@ user4122451の解決策のように)が、一時ファイルを作成していない、ともあれば失敗するsudo apt-get updateいくつかを出力せずに戻ってゼロ以外の終了コードをW:E:またはErr:文字列:

exec {fd}>&2 # copy stderr to some unused fd
bash -o pipefail -c "sudo apt-get update -y -q 2>&1 | tee /dev/fd/$fd | ( ! grep -q -e '^Err:' -e '^[WE]:' )"
result=$?
exec {fd}>&- # close file descriptor

具体的には、このソリューションはset -o pipefailbashオプションに依存し(パイプラインが右端のコマンドの値を返し、ゼロ以外のステータスで終了するようにします。それ以外の場合はゼロ)、追加の番号付きファイル記述子を使用します(このSO回答も参照)。

pipefailオプションをローカルにする必要がない場合は、次のように書くこともできます。

set -o pipefail
exec {fd}>&2 # copy stderr to some unused fd
sudo apt-get update -y -q 2>&1 | tee /dev/fd/$fd | ( ! grep -q -e '^Err:' -e '^[WE]:' )
result=$?
exec {fd}>&- # close file descriptor
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.