Bagaimana cara membuat frasa khusus yang dapat diperluas dalam bash?

12

Saya menemukan diri saya melakukan <command> --help | grep <feature>sangat sering setiap hari. Saya bertanya-tanya apakah mungkin membuat sesuatu seperti ^^itu mengembang "--help | grep"dan kemudian saya melakukan ini:

ls ^^ size

Itu akan menjalankan yang berikut:

ls --help | grep size
yukashima huksay
sumber

Jawaban:

17

Anda dapat menggunakan fungsi bash untuk itu:

Masukkan yang berikut ini di ~ / .bashrc Anda:

qh() {
    type -all "$1" ; { man "$1" || "$1" --help ;} | egrep -i -- "$2"
}

Ketika Anda menyimpan bashrc do source ~/.bashrcAnda maka Anda dapat melakukan:

$ qh ls size
      --block-size=SIZE      scale sizes by SIZE before printing them; e.g.,
                               '--block-size=M' prints sizes in units of
  -h, --human-readable       with -l and/or -s, print human readable sizes
  -s, --size                 print the allocated size of each file, in blocks
  -S                         sort by file size, largest first
      --sort=WORD            sort by WORD instead of name: none (-U), size (-S),
  -T, --tabsize=COLS         assume tab stops at each COLS instead of 8
tgwtdt
sumber
1
Anda harus mengutip $ 1 dan $ 2. Saya akan mengubah ini menjadi: qh () { type -all "$1" ; { "$1" --help || man "$1" ;} | egrep -i -- "$2" ;} # maka Anda bisa: qh ls size, qh ls "something | another" etc. the (optionnal) type -all "$1"juga menambahkan info tentang $ 1: dikatakan jika Anda akan meluncurkan alias, fungsi, dan perintah, dll. Dan itu memberikan info dari man "$ 1" jika perintah $ 1 tidak memiliki opsi "--help" (ini kadang-kadang terjadi)
Olivier Dulac
1
@OlivierDulac Bisakah Anda jelaskan sedikit tentang tipe -all "$ 1"? Dalam hal apa itu akan menjadi keharusan?
tgwtdt
Versi tipe saya (kubuntu 16.04) tahu tentang -a, tetapi tidak mengatakan apa-apa tentang -latau -all, tetapi fungsi tidak bekerja.
Joe
15

Dengan zsh, Anda akan menggunakan alias global :

$ alias -g '^^=--help|grep --color -i'
$ ls ^^ size
     --block-size=SIZE      scale sizes by SIZE before printing them; e.g.,
                              '--block-size=M' prints sizes in units of
                              1,048,576 bytes; see SIZE format below
 -h, --human-readable       with -l and/or -s, print human readable sizes
 -s, --size                 print the allocated size of each file, in blocks
 -S                         sort by file size, largest first
     --sort=WORD            sort by WORD instead of name: none (-U), size (-S),
 -T, --tabsize=COLS         assume tab stops at each COLS instead of 8
The SIZE argument is an integer and optional unit (example: 10K is 10*1024)

Dengan bash, Anda mungkin dapat menggunakan ekspansi histori yang merupakan salah satu yang terjadi cukup awal pada penguraian shell yang dapat digunakan untuk mengganti pipa:

  1. Perdana sejarah dengan teks yang ingin Anda gantikan dan karakter khusus Anda tidak mungkin menggunakan sebaliknya (seperti di £sini yang kebetulan ada di keyboard saya):

     $ --help $(: £)|grep
     bash: --help: command not found
     Usage: grep [OPTION]... PATTERN [FILE]...
     Try 'grep --help' for more information.
  2. Kemudian gunakan ekspansi riwayat untuk mengambil itu:

    $ ls !?£? size
    ls --help $(: £)|grep size
         --block-size=SIZE  scale sizes by SIZE before printing them; e.g.,
                              '--block-size=M' prints sizes in units of
     -h, --human-readable   with -l and/or -s, print human readable sizes
     -s, --size             print the allocated size of each file, in blocks
     -S                     sort by file size, largest first
         --sort=WORD        sort by WORD instead of name: none (-U), size (-S),
     -T, --tabsize=COLS     assume tab stops at each COLS instead of 8

Atau Anda dapat readlinememperluas --help|grepbeberapa tombol atau urutan tombol tekan. Untuk itu bashhanya berlaku untuk (dan bukan aplikasi lain seperti gdbmenggunakan readline), Anda dapat menggunakan perintah bindbash builtin yang merupakan bashAPI untuk mengkonfigurasi readline, misalnya di ~/.bashrc:

bind '"^^": "--help|grep "'

Atau tambahkan ke ~/.inputrc(file konfigurasi readline Anda):

$if Bash
"^^": "--help|grep "
$endif

(ada cangkang lain seperti rcatau esyang menggunakan readline dan di mana melakukan pengikatan itu masuk akal tetapi AFAICT, mereka tidak mengatur rl_readline_namevariabel sebelum memohon readlinesehingga Anda tidak akan dapat menambahkan beberapa $ifpernyataan untuk mereka (mereka akan ditampilkan otherseperti semua aplikasi yang menggunakan readline tanpa memberi tahu nama aplikasi mereka)).

Perhatikan bahwa Anda harus memasukkan yang kedua ^dalam waktu setengah detik (secara default) setelah yang pertama agar terjadi substitusi.

Stéphane Chazelas
sumber
Bisakah Anda jelaskan solusi readline sedikit lebih banyak? di mana saya harus menambahkan ikatan itu? pada aplikasi apa yang mengikat akan berkembang?
yukashima huksay
@yukashimahuksay, lihat edit
Stéphane Chazelas
8

Anda dapat menggunakan binding readline:

tambahkan garis seperti

"^^": "--help | grep "

ke ~ / .inputrc Anda

Kemudian tekan ^ X ^ R dalam jangka waktu Anda, dan penjilidan akan diaktifkan.

Penguncian ls ^^sekarang akan menghasilkan ls --help | grep.

Alex Stragies
sumber
Saya menjawab sebelum saya melihat, bahwa Stephane telah menambahkan solusi readline. Saya menghapus jawaban saya, tetapi kemudian terhapus, ketika saya melihat komentar bertanya tentang perincian untuk solusi readline
Alex Stragies
2
Saya sekarang telah menambahkan beberapa tentang itu dalam jawaban saya.
Stéphane Chazelas
1
Jawaban yang ditargetkan seperti milik Anda, dan jawaban yang komprehensif seperti Stéphane's, keduanya memiliki tempat masing-masing. Dapatkan upvote!
Uskup
5

Menggunakan lessuntuk melihat pesan bantuan

Anda mungkin menemukan berguna untuk melihat konteks garis yang sesuai dengan permintaan pencarian Anda.

hh () { "${1}" --help | less -p "${2}" ; }

Sintaks untuk memanggil bashfungsi ini mirip dengan fungsi qhdalam jawaban @ tgwtdt, dengan argumen pertama adalah perintah untuk memeriksa, dan argumen kedua adalah istilah pencarian. Sebagai contoh:

hh ls size
hh ls "symbolic link"

Ini membuka pesan bantuan lengkap less, menyoroti setiap instance dari istilah pencarian, dan menggulir ke instance pertama dari istilah pencarian. Anda kemudian dapat menekan nuntuk menggulir maju ke baris berikutnya yang berisi istilah pencarian, nlagi untuk berikutnya, dan seterusnya. Untuk menggulir kembali ke instance sebelumnya, tekan N. Gunakan Home, End, Page Up, Page Down, Up Arrow, dan Down Arrowtombol untuk navigasi umum. Tekan qatau Quntuk keluar lessdan kembali ke baris perintah.

Gaultheria
sumber
3

Saya menyukai solusinya dengan @tgwtdt, jadi saya sedikit meningkatkannya.

Ini melakukan hal yang sama, tetapi melakukan sedikit untuk menangani kesalahan dan juga mencoba untuk memproses built-in.

qh using () bukan {} so qh1 () dan out adalah lokal (dalam subkulit).

function qh () (
    function qh1 () {
      out="$(help "$1" 2>&1 )"
      [ $? -ne 0 ] && return 1
      echo "$out"
    }

    type -all "$1" ; { qh1 "$1" || "$1" --help 2>/dev/null || man "$1" 2>/dev/null ;} | egrep -i -- "$2"
) 
Joe
sumber