Saya menjalankan Ubuntu Linux. Misalkan ada program yang disebut myprogram
. Program ini meminta input dari pengguna; khusus, pengguna harus mengetik bilangan bulat ketika diminta dan tekan Enter. Saya ingin mengotomatiskan proses ini menggunakan skrip bash. Secara khusus, saya ingin mengeksekusi myprogram
, katakanlah, 100 kali (menggunakan penghitung i
yang beralih dari 1
ke 100
). Pada setiap eksekusi myprogram
, saya ingin memasukkan nilai saat ini i
ketika diminta.
(Omong-omong, myprogram
mengambil opsi / switch -options
, yang semuanya akan konstan dan dengan demikian ditentukan dalam skrip bash.)
Kerangka skrip bash yang tidak lengkap ini mungkin:
#!/bin/bash
for i in {1..100}
do
myprogram -options
done
Sekarang saya ingin memodifikasi kode di atas sehingga nilai saat i
ini dimasukkan ketika diminta oleh program. Apa cara terbaik untuk melakukan ini?
Situs web perangkat lunak yang saya gunakan menyarankan penggunaan <<EOF
di akhir myprogram -options
baris. Saya pikir ini memberitahu bash untuk melihat "akhir file" untuk input yang akan digunakan. Tetapi bagaimana jika saya tidak ingin menempatkan input di akhir file? Bagaimana jika saya ingin meletakkannya segera setelah <<
atau <
?
Alasannya adalah bahwa hal-hal akan menjadi lebih rumit. Sebagai contoh, saya dapat memperkenalkan penghitung bilangan bulat j
yang berubah dalam beberapa cara non-linear, non-sekuensial. Saya kemudian ingin memberi makan nilai saat ini j
untuk myprogram
pada setiap iterasi, tetapi nilai j
dapat berubah antara panggilan ke myprogram -options
dan akhir file EOF
.
Apakah Anda punya saran?
Jawaban:
Untuk hampir semua program, keduanya
echo $i | myprogram -options
danmyprogram -options <<<$i
harus bekerja, dengan memberi makan program$i
melalui input standar.<foo
akan menggunakan isi file bernamafoo
stdin.<<foo
akan menggunakan teks antara itu dan garis yang hanya terdiri darifoo
input standar. Ini adalah dokumen di sini (heredoc), seperti yang dikatakan Gilles;EOF
sebenarnya bukan berarti akhir dari file, itu hanya delineator heredoc yang umum (kita menggunakan "foo" sebagai gantinya dalam contoh ini).<<<foo
akan menggunakan string "foo" sebagai input standar. Anda juga dapat menentukan variabel$foo
, dan shell akan menggunakan isinya sebagai stdin, seperti yang saya tunjukkan di atas. Ini disebut herestring , karena menggunakan string pendek berbeda dengan seluruh blok, seperti dalam heredoc. Herestrings bekerja di bash, tetapi tidak di/bin/sh
.sumber
Sintaks yang direkomendasikan oleh situs web ini disebut dokumen di sini . Input ke program file dimulai segera di bawah baris yang berisi
<<EOF
, dan itu tidak diakhiri pada akhir skrip, tetapi oleh baris yang berisi teks secara persisEOF
(berhati-hatilah untuk tidak memiliki spasi tambahan). Omong-omong, Anda dapat menggunakan penanda akhir apa pun yang tidak mengandung karakter khusus shell:EOF
bukan kata kunci, itu hanya tradisional.sumber
END_OF_WHATEVER_FUNCTION
. Terkadang, mencoba untuk "menghemat" ruang / ukuran sebenarnya merupakan usaha yang sia-sia karena menyebabkan ambiguitas tentang apa yang sebenarnya terjadi.sleep
di antara perintah membaca dari skrip?di sini dokumen seperti yang disebutkan oleh Kevin dan Gilles di atas, atau perpipaan sederhana akan berfungsi dalam banyak kasus.
Untuk situasi yang lebih rumit, Anda mungkin ingin melihat Expect atau yang serupa (misalnya modul Expect :: Simple CPAN adalah implementasi perl yang sangat mudah digunakan). secara pribadi, saya lebih suka modul perl (Harapkan itu sendiri tcl) tetapi ada implementasi untuk banyak bahasa scripting umum. Bahkan mungkin untuk menulis implementasi ide yang sangat primitif di sh atau bash menggunakan saat dan membaca.
Gagasan umum Expect dan alat-alat serupa adalah menunggu string atau pola yang ditentukan dalam output suatu program, dan kemudian mengumpankannya input apa pun yang Anda inginkan.
Contoh umum yang digunakan adalah mengotomatiskan login, dengan "mengharapkan" (yaitu menunggu) string "ogin:", mengirim nama login, lalu mengharapkan string "kata:" dan mengirim kata sandi.
Satu opsi terakhir, jika Anda memiliki sumber myprogram, adalah memodifikasinya untuk mengambil input yang ingin Anda berikan sebagai opsi baris perintah. Ini mungkin sedikit lebih banyak bekerja di muka, tetapi akan jauh lebih memberatkan daripada bermain-main dengan Expect atau memipipkan data ke dalam program yang tidak dirancang untuk digunakan dengan cara itu.
... dan jangan lupa untuk mengirimkan tambalan Anda ke myprogram kembali hulu :) Bahkan jika mereka tidak suka cara Anda mengkodekannya, mereka mungkin cukup menyukai ide untuk menambahkan fitur itu sendiri. Pengembang hulu cenderung menghargai orang-orang yang keluar dari pantat mereka dan berkontribusi daripada menuntut atau mengeluh.
sumber