In zsh (oltre a bash) puoi usare alcune espansioni di parole della cronologia per indicare argomenti di comandi precedenti.
Questo esempio mostra come ottenere il 2o parametro dal comando precedente nella cronologia con !:#
espansione:
% echo foo bar baz
foo bar baz
% echo !:2
echo bar
bar
Spesso dimentico esattamente quale sia il parametro # di un particolare argomento e la digitazione !:#
non è sempre così rapida quando ricordo quale argomento . So meta-.
di sostituire l'ultimo argomento, ma a volte non è l'ultimo argomento che voglio.
Vorrei aggiungere gli argomenti del comando precedente come suggerimenti per completare qualsiasi comando che sto scrivendo in zsh.
Sono stato in grado di capire come creare una funzione di shell in grado di creare una matrice di argomenti (0..N) dall'ultimo comando e associarlo a un comando particolare.
_last_command_args() {
last_command=$history[$[HISTCMD-1]]
last_command_array=("${(s/ /)last_command}")
_sep_parts last_command_array
}
# trying to get last_command_args to be suggested for any command, this just works for foo
compdef _last_command_args foo
Questo è quello che sembra per aver completato solo il punto in cui ho premuto il tasto Tab su <TAB>
:
% echo bar baz qux
bar baz qux
% foo <TAB>
bar baz echo qux
Funziona benissimo per completare il comando "pippo", ma vorrei che fossero opzioni su qualsiasi espansione zsh che faccio. Penso che abbia qualcosa a che fare con le cose del completatore di zstyle, ma dopo alcune ore di hacking ho capito di essere fuori dalla mia profondità.
Come posso ottenere gli argomenti dal mio comando precedente come completamenti suggeriti per qualsiasi comando in zsh?
Ho tutto il mio file compinstall zshrc condiviso su bitbucket se questo aiuta. Molti di questi sono paralizzati da una varietà di fonti e alcuni di essi li ho hackerati insieme.
AGGIORNARE:
@Julien La risposta di Nicoulaud mi ha avvicinato, la sto contrassegnando come accettata in quanto mi ha portato dove dovevo trovare.
Con la mia configurazione particolare, usando il suggerito:
zstyle ':completion:*' completer _last_command_args _complete
Non ha funzionato abbastanza per me poiché stava causando il completamento della scheda per visualizzare solo l'elenco degli argomenti dell'ultimo comando (anche se in realtà sarebbe completo anche di nomi di file, ma non li visualizzava). Cambiando l'ordine per _complete _last_command_args
fare il contrario. Visualizzerebbe i nomi di file normali, ma non last_command_args
Immagino che questo abbia qualcosa a che fare con il modo in cui funziona il completatore. Penso che visualizzi solo l'output del primo metodo che ritorna correttamente, ma ho problemi ad analizzare la fonte zsh per capire appieno cosa sta succedendo. Sono stato in grado di modificare il mio metodo per includere una chiamata in _complete
modo che mostrasse sia i comandi dell'ultimo argomento sia i normali elementi di completamento automatico. Non abbastanza separato, ma funziona abbastanza bene per me.
Ecco la funzione completa che ho usato insieme alle altre cose di zstyle che ho:
# adds the arguments from the last commadn to the autocomplete list
# I wasn't able to get this to work standalone and still print out both regular
# completion plus the last args, but this works well enough.
_complete_plus_last_command_args() {
last_command=$history[$[HISTCMD-1]]
last_command_array=("${(s/ /)last_command}")
_sep_parts last_command_array
_complete
}
_force_rehash() {
(( CURRENT == 1 )) && rehash
return 1 # Because we didn't really complete anything
}
zstyle ':completion:::::' completer _force_rehash _complete_plus_last_command_args _approximate
Altre linee di zstyle che ho, non necessarie per farlo funzionare, ma potrebbero influenzare il motivo per cui questo funziona per me:
zstyle -e ':completion:*:approximate:*' max-errors 'reply=( $(( ($#PREFIX + $#SUFFIX) / 3 )) )'
zstyle ':completion:*:descriptions' format "- %d -"
zstyle ':completion:*:corrections' format "- %d - (errors %e})"
zstyle ':completion:*:default' list-prompt '%S%M matches%s'
zstyle ':completion:*' group-name ''
zstyle ':completion:*:manuals' separate-sections true
zstyle ':completion:*' menu select
zstyle ':completion:*' verbose yes
Ora, se sono in una directory con file1.txt
e file2.txt
, e il mio ultimo comando è stato echo foo bar baz
, ottengo questo per il completamento automatico che è proprio quello che volevo:
% ls
bar baz echo foo
- files -
file1.txt file2.txt
^[ .
( insert-last-word
), mi piace copy-earlier-word
, che scorre tra le parole della riga raggiunte da insert-last-word
. Per il tuo .zshrc
:autoload copy-earlier-word && zle -N copy-earlier-word && bindkey '^[,' copy-earlier-word