Saya memiliki skrip bash yang kira-kira seperti ini:
#!/bin/bash
if [ $1 = "--test" ] || [ $1 = "-t" ]; then
echo "Testing..."
testing="y"
else
testing="n"
echo "Not testing."
fi
Jadi apa yang ingin saya lakukan tidak hanya menjalankannya dengan ./script --test
atau ./script -t
, tetapi juga tanpa argumen (adil ./script
), tetapi tampaknya jika saya melakukannya dengan kode saat ini, outputnya hanya:
./script: line 3: [: =: unary operator expected
./script: line 3: [: =: unary operator expected
Not testing.
Jadi bagaimana saya memprogramnya sehingga menjalankannya tanpa argumen sama sekali hanya akan melakukan else
tanpa membuang kesalahan? Apa yang saya lakukan salah?
command-line
bash
scripts
Peter Cordes
sumber
sumber
Jawaban:
"Cara yang tepat" untuk menggunakan opsi panjang dalam skrip shell adalah melalui utilitas getopt GNU . Ada juga getopt yang merupakan bash built-in , tetapi hanya memungkinkan opsi pendek seperti
-t
. Beberapa contohgetopt
penggunaan dapat ditemukan di sini .Berikut ini skrip yang menunjukkan cara saya mendekati pertanyaan Anda. Penjelasan sebagian besar langkah ditambahkan sebagai komentar di dalam skrip itu sendiri.
Dengan beberapa penyederhanaan dan komentar yang dihapus, ini dapat disingkat menjadi:
sumber
Beberapa cara; dua yang paling jelas adalah:
$1
tanda kutip ganda:if [ "$1" = "--test" ]
Lebih baik lagi, gunakan getopts.
sumber
[ "x$1" = "x--test" ]
untuk mempertahankan lagi argumen baris perintah yang merupakan operator yang valid untuk[
perintah tersebut. (Ini adalah alasan lain mengapa[[ ]]
lebih disukai: itu bagian dari sintaks shell, bukan hanya perintah builtin.)Anda perlu mengutip variabel Anda di dalam kondisi if. Menggantikan:
dengan:
Maka akan berhasil:
Selalu selalu gandakan penawaran variabel Anda!
sumber
foo=bar echo '$foo'
cetakan ekspansi variabel$foo
ke output, tetapifoo=bar echo "$foo"
dicetakbar
sebagai gantinya.Anda menggunakan bash. Bash memiliki alternatif untuk
[
:[[
. Dengan[[
, Anda tidak perlu khawatir apakah akan mengutip, dan Anda mendapatkan lebih banyak operator daripada[
, termasuk dukungan yang tepat untuk||
:Atau Anda dapat menggunakan ekspresi reguler:
Tentu saja, mengutip yang benar harus selalu dilakukan, tetapi tidak ada alasan untuk tetap
[
menggunakan bash.sumber
Untuk menguji apakah ada argumen (secara umum, dan melakukan tindakan yang sesuai) Ini harus bekerja:
sumber
[ -z "$1" ]
?$check
satu kali, sebelum adashift
, jadi akan lebih baik untuk menggunakannya$1
.#!
saat memberikan sampel (Anda harus menggambarkan shell di luar kode).