diff --git a/code/productivity/qvm-cmds-bash-completion.bash b/code/productivity/qvm-cmds-bash-completion.bash new file mode 100644 index 0000000..d3a51ba --- /dev/null +++ b/code/productivity/qvm-cmds-bash-completion.bash @@ -0,0 +1,183 @@ +# qvm-* commands bash auto completion + +# Copy this file to /etc/bash_completion.d/qvm.bash + +# idea from https://www.mail-archive.com/qubes-users@googlegroups.com/msg20088.html + +# taraddidles - apr 2018 + + + +# COMPLETION FUNCTIONS +# ==================== + +# Output the relative position of COMP_CWORD when words beginning with '-' are ignored +# Note: this logic is flawed when using option arguments (eg. -s blah). +# Unfortunately there is now way to solve this except parsing every +# known option for a given qvm-* command +_get-cword() { + local index=0 + local i + for ((i=1; i<=COMP_CWORD; i++)); do + [[ ${COMP_WORDS[i]} == -* ]] && continue + let index++ + done + echo ${index} +} + +# Output the first element in COMP_WORDS that doesn't begin with '-' +# Note: this logic is flawed when using option arguments (eg. -s blah). +# Unfortunately there is now way to solve this except parsing every +# known option for a given qvm-* command +_get-first-word() { + local i + for ((i=1; i<=COMP_CWORD; i++)); do + [[ ${COMP_WORDS[i]} == -* ]] && continue + echo ${COMP_WORDS[i]} + return 0 + done + echo "" +} + +_complete-vms() { + local vms + local state="${1}" + local cur="${COMP_WORDS[COMP_CWORD]}" + case "${state}" in + runtrans) + vms=$(qvm-ls --raw-data | grep -i "|\(Running\|Transient\)|" | cut -f1 -d"|") + ;; + running|halted|paused) + vms=$(qvm-ls --raw-data | grep -i "|${state}|" | cut -f1 -d"|") + ;; + "") + vms=$(qvm-ls --raw-list) + ;; + esac + COMPREPLY=( $(compgen -W "${vms}" -- "${cur}") ) + return 0 +} + +_complete-filenames() { + local cur="${COMP_WORDS[COMP_CWORD]}" + COMPREPLY=( $(compgen -f -- "$cur") ) + return 0 +} + +_complete-vmprops() { + local vm="${1}" + local property="${2}" + local props + local cur="${COMP_WORDS[COMP_CWORD]}" + if qvm-check "${vm}" > /dev/null 2>&1; then + case "${property}" in + prefs) + props=$(qvm-prefs "${vm}" | cut -f1 -d " ") + ;; + features) + props=$(qvm-features "${vm}" | cut -f1 -d " ") + ;; + tags) + props=$(qvm-tags "${vm}" | cut -f1 -d " ") + ;; + esac + fi + COMPREPLY=( $(compgen -W "${props}" -- "${cur}") ) +} + + + +# WRAPPERS and COMPLETE functions +# =============================== + +#----- args: vm(all) ----- +_qvm-vms-all-all() { + _complete-vms "" +} +complete -F _qvm-vms-all-all qvm-backup + + +#----- arg1: vm(all) ----- +_qvm-vms-all() { + [ $(_get-cword ${COMP_CWORD}) = 1 ] && _complete-vms "" +} +complete -F _qvm-vms-all qvm-check +complete -F _qvm-vms-all qvm-clone +complete -F _qvm-vms-all qvm-firewall +complete -F _qvm-vms-all qvm-remove +complete -F _qvm-vms-all qvm-run +complete -F _qvm-vms-all qvm-service +complete -F _qvm-vms-all qvm-start-gui +complete -F _qvm-vms-all qvm-usb + + +#----- arg1: vm(halted) ----- +_qvm-vms-halted() { + [ $(_get-cword ${COMP_CWORD}) = 1 ] && _complete-vms "halted" +} +complete -F _qvm-vms-halted qvm-start + + +#----- arg1: vm(paused) ----- +_qvm-vms-paused() { + [ $(_get-cword ${COMP_CWORD}) = 1 ] && _complete-vms "paused" +} +complete -F _qvm-vms-paused qvm-unpause + + +#----- arg1: vm(running) ----- +_qvm-vms-running() { + [ $(_get-cword ${COMP_CWORD}) = 1 ] && _complete-vms "running" +} +complete -F _qvm-vms-running qvm-pause +complete -F _qvm-vms-running qvm-shutdown + + +#----- arg1: vm(running|transient) ----- +_qvm-vms-runtrans() { + [ $(_get-cword ${COMP_CWORD}) = 1 ] && _complete-vms "runtrans" +} +complete -F _qvm-vms-runtrans qvm-kill + + +#----- arg1: vm(all) ; arg(>=2): filenames ----- +_qvm-vms-all-filenames() { + if [ "$(_get-cword ${COMP_CWORD})" -eq 1 ]; then + _complete-vms "" + else + _complete-filenames + fi +} +complete -F _qvm-vms-all-filenames qvm-copy-to-vm +complete -F _qvm-vms-all-filenames qvm-move-to-vm + + +#----- arg1: vm(all) ; arg2: vm preferences ----- +_qvm-vms-all-vmprefs() { + case "$(_get-cword ${COMP_CWORD})" in + 1) _complete-vms "" ;; + 2) _complete-vmprops "$(_get-first-word)" "prefs";; + esac +} +complete -F _qvm-vms-all-vmprefs qvm-prefs + + +#----- arg1: vm(all) ; arg2: vm features ----- +_qvm-vms-all-vmfeatures() { + case "$(_get-cword ${COMP_CWORD})" in + 1) _complete-vms "" ;; + 2) _complete-vmprops "$(_get-first-word)" "features";; + esac +} +complete -F _qvm-vms-all-vmfeatures qvm-features + + +#----- arg1: vm(all) ; arg2: vm tags ----- +_qvm-vms-all-vmtags() { + case "${COMP_CWORD}" in + 1) _complete-vms "" ;; + 2) _complete-vmprops "$(_get-first-word)" "tags";; + esac +} +complete -F _qvm-vms-all-vmtags qvm-tags + diff --git a/code/productivity/qvm-cmds-bash-completion.sh b/code/productivity/qvm-cmds-bash-completion.sh deleted file mode 100644 index 4b8b712..0000000 --- a/code/productivity/qvm-cmds-bash-completion.sh +++ /dev/null @@ -1,52 +0,0 @@ -# qvm-* commands bash auto completion - -# copy this file to /etc/bash_completion.d/qvm.sh -# make sure 'bash-completion' is installed (sudo qubes-dom0-update bash-completion) - -# credit: https://www.mail-archive.com/qubes-users@googlegroups.com/msg20088.html - -_qvm() -{ - local cur vms - local state=${1} - COMPREPLY=() - cur="${COMP_WORDS[COMP_CWORD]}" - case ${state} in - running|halted|paused) - vms=$(qvm-ls --raw-data | grep -i "|${state}|" | cut -f1 -d"|") - ;; - "") - vms=$(qvm-ls --raw-list) - ;; - *) vms="" - esac - COMPREPLY=( $(compgen -W "${vms}" ${cur}) ) - return 0 -} - -_qvmall() { _qvm ""; } -_qvmrunning() { _qvm "running"; } -_qvmhalted() { _qvm "halted"; } -_qvmpaused() { _qvm "paused"; } - -complete -F _qvmall qvm-appmenus -complete -F _qvmall qvm-backup -complete -F _qvmall qvm-backup-restore -complete -F _qvmall qvm-check -complete -F _qvmall qvm-clone -complete -F _qvmall qvm-copy-to-vm -complete -F _qvmall qvm-features -complete -F _qvmall qvm-firewall -complete -F _qvmall qvm-move-to-vm -complete -F _qvmall qvm-prefs -complete -F _qvmall qvm-remove -complete -F _qvmall qvm-run -complete -F _qvmall qvm-service -complete -F _qvmall qvm-start-gui -complete -F _qvmall qvm-tags -complete -F _qvmall qvm-usb -complete -F _qvmhalted qvm-start -complete -F _qvmpaused qvm-unpause -complete -F _qvmrunning qvm-kill -complete -F _qvmrunning qvm-pause -complete -F _qvmrunning qvm-shutdown