GNU/Linux >> Belajar Linux >  >> Linux

Trik Bash yang lebih bodoh:Variabel, temukan, deskriptor file, dan operasi jarak jauh

Posting blog ini adalah yang kedua dari dua yang mencakup beberapa tip dan trik praktis untuk mendapatkan hasil maksimal dari shell Bash. Di bagian pertama, saya membahas sejarah, argumen terakhir, bekerja dengan file dan direktori, membaca file, dan fungsi Bash. Di segmen ini, saya membahas variabel shell, find, deskriptor file, dan operasi jarak jauh.

Gunakan variabel shell

Variabel Bash diatur oleh shell saat dipanggil. Mengapa saya menggunakan hostname kapan saya bisa menggunakan $HOSTNAME, atau mengapa saya menggunakan whoami kapan saya bisa menggunakan $USER? Variabel Bash sangat cepat dan tidak memerlukan aplikasi eksternal.

Ini adalah beberapa variabel yang sering digunakan:

$PATH
$HOME
$USER
$HOSTNAME
$PS1
..
$PS4

Gunakan echo perintah untuk memperluas variabel. Misalnya, variabel shell $PATH dapat diperluas dengan menjalankan:

$> echo $PATH

[ Unduh sekarang:Panduan sysadmin untuk skrip Bash. ]

Gunakan perintah find

find command mungkin adalah salah satu alat yang paling banyak digunakan dalam sistem operasi Linux. Ini sangat berguna dalam shell interaktif. Ini juga digunakan dalam skrip. Dengan find Saya dapat membuat daftar file yang lebih lama atau lebih baru dari tanggal tertentu, menghapusnya berdasarkan tanggal tersebut, mengubah izin file atau direktori, dan seterusnya.

Mari kita lebih mengenal perintah ini.

Untuk membuat daftar file yang lebih lama dari 30 hari, saya cukup menjalankan:

$> find /tmp -type f -mtime +30

Untuk menghapus file yang lebih lama dari 30 hari, jalankan:

$> find /tmp -type f -mtime +30 -exec rm -rf {} \;

atau

$> find /tmp -type f -mtime +30 -exec rm -rf {} +

Sementara perintah di atas akan menghapus file yang lebih lama dari 30 hari, seperti yang tertulis, perintah tersebut mem-fork rm perintah setiap kali mereka menemukan file. Pencarian ini dapat ditulis lebih efisien dengan menggunakan xargs :

$> find /tmp -name '*.tmp' -exec printf '%s\0' {} \; | xargs -0 rm

Saya dapat menggunakan find untuk membuat daftar sha256sum file hanya dengan menjalankan:

$> find . -type f -exec sha256sum {} +

Dan sekarang untuk mencari dan menghapus file .jpg duplikat:

$> find . -type f -name '*.jpg' -exec sha256sum {} + | sort -uk1,1 

Descriptor file referensi

Di shell Bash, deskriptor file (FD) penting dalam mengelola input dan output perintah. Banyak orang memiliki masalah dalam memahami deskriptor file dengan benar. Setiap proses memiliki tiga deskriptor file default, yaitu:

Kode Arti Lokasi Deskripsi
0 Masukan standar /dev/stdin Keyboard, file, atau aliran tertentu
1 Keluaran standar /dev/stdout Monitor, terminal, tampilan
2 Kesalahan standar /dev/stderr Kode keluar bukan nol biasanya>FD2, tampilan

Sekarang setelah Anda mengetahui apa yang dilakukan FD default, mari kita lihat aksinya. Saya mulai dengan membuat direktori bernama foo , yang berisi file1 .

$> ls foo/ bar/
ls: cannot access 'bar/': No such file or directory
foo/:
file1

Keluaran Tidak ada file atau direktori seperti itu pergi ke Standard Error (stderr) dan juga ditampilkan di layar. Saya akan menjalankan perintah yang sama, tetapi kali ini menggunakan 2> untuk menghilangkan stderr:

$> ls foo/ bar/ 2>/dev/null
foo/:
file1

Dimungkinkan untuk mengirim output foo ke Output Standar (stdout) dan ke file secara bersamaan, dan abaikan stderr. Misalnya:

$> { ls foo bar | tee -a ls_out_file ;} 2>/dev/null
foo:
file1

Kemudian:

$> cat ls_out_file
foo:
file1

Perintah berikut mengirim stdout ke file dan stderr ke /dev/null agar kesalahan tidak muncul di layar:

$> ls foo/ bar/ >to_stdout 2>/dev/null
$> cat to_stdout
foo/:
file1

Perintah berikut mengirim stdout dan stderr ke file yang sama:

$> ls foo/ bar/ >mixed_output 2>&1
$> cat mixed_output
ls: cannot access 'bar/': No such file or directory
foo/:
file1

Inilah yang terjadi pada contoh terakhir, di mana stdout dan stderr dialihkan ke file yang sama:

    ls foo/ bar/ >mixed_output 2>&1
             |          |
             |          Redirect stderr to where stdout is sent
             |                                                        
             stdout is sent to mixed_output

Trik singkat lainnya (> Bash 4.4) untuk mengirim stdout dan stderr ke file yang sama menggunakan tanda ampersand. Misalnya:

$> ls foo/ bar/ &>mixed_output

Berikut adalah pengalihan yang lebih kompleks:

exec 3>&1 >write_to_file; echo "Hello World"; exec 1>&3 3>&-

Inilah yang terjadi:

  • exec 3>&1                      Salin stdout ke deskriptor file 3
  • > write_to_file              Buat FD 1 untuk menulis ke file
  • echo "Hello World"     Buka file karena FD 1 sekarang menunjuk ke file
  • exec 1>&3                      Salin FD 3 kembali ke 1 (tukar)
  • Tiga>&-                       Tutup deskriptor file tiga (kami tidak membutuhkannya lagi)

Seringkali berguna untuk mengelompokkan perintah, dan kemudian mengirim Output Standar ke satu file. Misalnya:

$> { ls non_existing_dir; non_existing_command; echo "Hello world"; } 2> to_stderr
Hello world

Seperti yang Anda lihat, hanya "Hello world" yang tercetak di layar, tetapi output dari perintah yang gagal ditulis ke file to_stderr.

Jalankan operasi jarak jauh

Saya menggunakan Telnet, netcat, Nmap, dan alat lain untuk menguji apakah layanan jarak jauh aktif dan apakah saya dapat terhubung ke sana. Alat ini berguna, tetapi tidak diinstal secara default di semua sistem.

Untungnya, ada cara sederhana untuk menguji koneksi tanpa menggunakan alat eksternal. Untuk melihat apakah server jarak jauh menjalankan web, database, SSH, atau layanan lainnya, jalankan:

$> timeout 3 bash -c ‘</dev/tcp/remote_server/remote_port’ || echo “Failed to connect”

Misalnya, untuk melihat apakah serverA sedang menjalankan layanan MariaDB:

$> timeout 3 bash -c ‘</dev/tcp/serverA/3306’ || echo “Failed to connect”

Jika koneksi gagal, Gagal terhubung pesan ditampilkan di layar Anda.

Asumsikan serverA berada di belakang firewall/NAT. Saya ingin melihat apakah firewall dikonfigurasi untuk mengizinkan koneksi database ke serverA , tapi saya belum menginstal server database. Untuk mengemulasi port database (atau port lainnya), saya dapat menggunakan yang berikut ini:

[serverA ~]# nc -l 3306

Di klienA , jalankan:

[clientA ~]# timeout 3 bash -c ‘</dev/tcp/serverA/3306’ || echo “Failed”

Saat saya membahas koneksi jarak jauh, bagaimana dengan menjalankan perintah pada server jarak jauh melalui SSH? Saya dapat menggunakan perintah berikut:

$> ssh remotehost <<EOF  # Press the Enter key here
> ls /etc
EOF

Perintah ini menjalankan ls /etc pada host jarak jauh.

Saya juga dapat menjalankan skrip lokal pada host jarak jauh tanpa harus menyalin skrip ke server jarak jauh. Salah satu caranya adalah dengan memasukkan:

$> ssh remote_host 'bash -s' < local_script

Contoh lain adalah meneruskan variabel lingkungan secara lokal ke server jauh dan mengakhiri sesi setelah eksekusi.

$> exec ssh remote_host ARG1=FOO ARG2=BAR 'bash -s' <<'EOF'
> printf %s\\n "$ARG1" "$ARG2"
> EOF
Password:
FOO
BAR
Connection to remote_host closed.

Ada banyak tindakan kompleks lainnya yang dapat saya lakukan pada host jarak jauh.

Menutup

Pasti ada lebih banyak hal di Bash daripada yang bisa saya bahas dalam posting blog dua bagian ini. Saya membagikan apa yang saya ketahui dan apa yang saya hadapi setiap hari. Idenya adalah untuk membiasakan Anda dengan beberapa teknik yang dapat membuat pekerjaan Anda tidak terlalu rawan kesalahan dan lebih menyenangkan.

[ Ingin menguji kemampuan sysadmin Anda? Ikuti penilaian keterampilan hari ini. ]


Linux
  1. Trik Bash Bodoh:Sejarah, menggunakan kembali argumen, file dan direktori, fungsi, dan banyak lagi

  2. Bash:Penggunaan Prosedural Find Into Select yang aman-spasi?

  3. Bagaimana Menemukan Jenis File Img Dan Memasangnya?

  1. Temukan File dengan Perintah Temukan dan Temukan di Linux

  2. Tip dan trik .htaccess Linux

  3. temukan dan salin file menggunakan Bash

  1. Ekstrak nama file dasar tanpa jalur dan ekstensi di bash

  2. Fungsi Bash untuk menemukan pola pencocokan file terbaru

  3. Utas dan deskriptor file