Bir değişken tanımlanmamışsa komut dosyasını çalıştırmaktan kaçının


18

Ben şöyle bir komut dosyası var:

c=0
for f in */*; do
cp -v "$f" "/myhome/CE$(printf '%0*d' 2 $BATCHNUM)-new-stuctures_extracted/test-$(printf '%0*d' 5 $c)"
c=$((c=c+1))
done

Ancak, kullanıcı değişken bir çağrı BATCHNUM sağlamalıdır ve aksi takdirde ben bu komut dosyası çalışmayı durdurmak zorlamak gerekir. Bu komut dosyasını çağıran komut dosyasını da (veya bu komut dosyasını çağıran # 2 komut dosyasını çağıran # 1 komut dosyasını) durmaya zorlayabilirsem daha iyi olur.

Yanıtlar:


30

En hızlı yol muhtemelen bu iki satırı komut dosyasının başına eklemektir:

set -u # or set -o nounset
: "$BATCHNUM"

İlk satır nounset, komut dosyasını çalıştıran kabukta, ayarlanmamış bir değişkeni genişletmeye çalıştığınızda iptal edilen seçeneği ayarlar ; ikincisi, $BATCHNUMbaşka bir şey yapmadan önce kürtajı tetiklemek için bir operasyon yok bağlamında genişler .

Daha yararlı bir hata mesajı istiyorsanız bunun yerine şunu yazabilirsiniz:

if [[ -z "$BATCHNUM" ]]; then
    echo "Must provide BATCHNUM in environment" 1>&2
    exit 1
fi

Veya benzeri.


18

Burada kontrol etmek istiyorsun BATCHNUM ayarlanmış ve boş değil.

POSIX kabuğu bu iş için bir Parametre Genişlemesi sağlar. Kullanmadan önce bu satırı eklemeniz yeterlidir BATCHNUM:

: "${BATCHNUM:?Variable not set or empty}"

veya BATCHNUMkullanıcı bir değer sağlamadıysa için varsayılan değeri ayarlamak için daha iyisi :

: "${BATCHNUM:=3}"

4
[ -n "$BATCHNUM" ] || { kill "$PPID"; exit 1; }
#Unless $BATCHNUM is defined and unempty, ask parent process to exit and exit w/ 1

Bu bash ve POSIX sh üzerinde çalışacaktır. Boş değişkenler ve tanımsız değişkenler arasında ayrım yapmamayı tercih ederim (yani, sevmiyorum set -u, ama bu sadece benim).


2

Çizgiler

if [ -z "$BATCHNUM" ]; then
    exit 2;
fi

boş olup olmadığını kontrol edin $BATCHNUM. İle $PPIDebeveyninize ( kill $PPID) istediğiniz her şeyi yapabilirsiniz . Büyükbaba veya büyükannenizi öldürmek için işlem kimliğini, içindeki verilere bakmak gibi başka yollarla almanız gerekir /proc/$PPID.

Bununla birlikte, ebeveyniniz ölürse, SIGHUPsize bir sinyal ( ) gönderir , bu nedenle kimseyi öldürmeye başlamadan önce onu tuzağa düşürmeniz gerekir:

trap '' SIGHUP

Güncelleme: Ailenizi öldürmeniz gerektiğini düşünüyorsanız, yanlış yapıyorsunuz. Anlamlı bir çıkış kodu döndürmeniz yeterlidir. Ana komut dosyası, çağrılan komut dosyasının dönüş kodunu kontrol etmeli ve buna göre tepki vermelidir.


1
biraz acımasız .... :)
user40780

1

BATCHNUMTanımlanmış olup olmadığını test etmek ve tanımlanmamışsa çıkmak için:

if [ -n "${BATCHNUM-a}" ]; then
  echo >&2 "Fatal error: BATCHNUM not set"
  exit 2
fi

Vakayı BATCHNUMboş olan yeri de reddetmek istiyorsanız , ${BATCHNUM:+a}yerine kullanın ${BATCHNUM+a}. Hakkında bilgi için ${VARIABLE+TEXT_IF_NULL}parametre genişletme yapı, örneğin bkz bash kılavuzu .

Üst süreci öldürmeyin. Üst sürecin ne olduğunu bilmiyorsunuz. Bu komut dosyasını çağıran bir komut dosyasının iptal edilmesi gerekiyorsa, bu komut dosyasının çıkış durumunu denetlemesini sağlayın. Örneğin, komut dosyası # 2:

script3 || exit $?

veya set -eherhangi bir komut bir hata (sıfır olmayan) durumu döndürürse komut dosyasını iptal etmek için kullanın .

Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.