Mengapa saya tidak bisa mendapatkan nilai keluar dari perintah dalam skrip bash ini?

9

Jadi saya menulis skrip nautilus kecil ini untuk mentranskode video ke mp3:

#! /bin/bash -x

if [ -z "$1" ]
    then
    zenity --warning --text="Error - No file selected !"
    exit 1
fi

BASEFILENAME=${1%.*}

exec ffmpeg -i "$1" -ab 256k "$BASEFILENAME.mp3" &&

if [ "$?" -eq 0 ]
    then
    zenity --info --text="Converting successful"
    exit
fi

Masalahnya adalah, meskipun perintah ffmpeg berhasil dijalankan if [ "$?" -eq 0 ]

sepertinya tidak dipicu. Mengapa demikian? Apakah yang &&salah atau itu sesuatu yang lain?

tesseract
sumber

Jawaban:

13

Satu-satunya cara agar pernyataan itu dapat dicapai adalah jika pernyataan execitu sendiri gagal; jika berhasil, ffmpegperintah akan menggantikan shell sepenuhnya. (Pedantically, &&akan gagal dalam kasus itu juga sehingga tidak dapat dicapai sama sekali.) Anda tidak mau exec, jalankan saja.

geekosaurus
sumber
Begitu, dan tanpa &&perintah ffmpeg setelah itu, ia benar-benar berfungsi. Saya masih punya satu pertanyaan lagi, apakah boleh di tempat ini - apakah ada cara untuk menampilkan stdout dan stderr ffmpeg di suatu tempat tanpa menggunakan jendela terminal? Seperti di zenity, fe
tesseract
Anda ingin menangkapnya dengan $()konstruk ke dalam variabel, lalu meneruskan variabel itu ke zenity. Watch out untuk mengutip, dan zenitydalam pengalaman saya menggunakan Pango sehingga Anda perlu mengganti <, &, >dengan &lt;, &amp;, &gt;masing-masing.
geekosaur
5

The exec commandpernyataan menggantikan shell saat ini dengan command. Artinya, skrip Anda secara aktuil berakhir pada baris exec ffmpeg ...; baris yang tersisa akan dieksekusi jika dan hanya jika ffmpegperintah tidak ditemukan di PATH Anda (atau tidak dapat diluncurkan karena alasan lain).

Anda bisa mendapatkan detail lebih lanjut tentang execbash built-in dengan mengetikkan help execpada prompt perintah bash:

$ help exec
exec: exec [-cl] [-a name] [command [arguments ...]] [redirection ...]
    Replace the shell with the given command.

    Execute COMMAND, replacing this shell with the specified program.
    ARGUMENTS become the arguments to COMMAND.  If COMMAND is not specified,
    any redirections take effect in the current shell.
    [...]
Riccardo Murri
sumber
1

Menurut ini exec menggantikan shell dengan perintah yang Anda tentukan. Jadi skrip Anda tidak pernah sampai ke perintah yang melewati exec.

Anda tidak perlu exec. Cukup tentukan perintahnya.

LawrenceC
sumber
0

Anda dapat menyimpan execperintah jika Anda memasukkannya ke dalam subkulit:

- exec ffmpeg -i "$1" -ab 256k "$BASEFILENAME.mp3" &&
+ (exec ffmpeg -i "$1" -ab 256k "$BASEFILENAME.mp3") &&
jeff
sumber
Begitu, tapi bukankah &&masih ada yang salah di sana?
tesseract
Iya. Dan apa gunanya menyimpannya exec?
jmtd