#compdef machinectl
+# SPDX-License-Identifier: LGPL-2.1-or-later
-(( $+functions[_machinectl_command] )) || _machinectl_command()
+(( $+functions[__machinectl_get_images] )) ||
+ __machinectl_get_images () {
+ local -a flags
+ if [[ $PREFIX == .* ]]; then flags=( --all ); fi
+ machinectl --no-legend list-images $flags | {while read -r a b; do
+ # escape : and \; do not interpret existing escape sequences
+ printf -- "%s\n" ${a//(#b)(\\|:)/\\$match}
+ done;}
+ }
+
+(( $+functions[_machinectl_images] )) ||
+ _machinectl_images() {
+ local -a _machines
+ _machines=("${(fo)$(__machinectl_get_images)}")
+ typeset -U _machines
+ if [[ -n "$_machines" ]]; then
+ _describe 'images' _machines
+ else
+ _message 'no images'
+ fi
+ }
+
+(( $+functions[_machinectl_commands] )) || _machinectl_commands()
{
- local -a _machinectl_cmds
- _machinectl_cmds=(
- "list:List currently running VMs/containers"
- "status:Show VM/container status"
- "show:Show properties of one or more VMs/containers"
- "terminate:Terminate one or more VMs/containers"
- "kill:Send signal to process or a VM/container"
- )
- if (( CURRENT == 1 )); then
- _describe -t commands 'machinectl command' _machinectl_cmds || compadd "$@"
- else
- local curcontext="$curcontext"
- cmd="${${_machinectl_cmds[(r)$words[1]:*]%%:*}}"
- if (( $#cmd )); then
- case $cmd in
- list) msg="no options" ;;
- *)
- _machines=( "${(foa)$(machinectl list | awk '{print $1}')}" )
- if [[ -n "$_machines" ]]; then
- _describe 'machines' _machines
- else
- _message 'no machines'
- fi
- esac
+ local -a _machinectl_cmds
+ _machinectl_cmds=(
+ "list:List currently running VMs/containers"
+ "status:Show VM/container status"
+ "show:Show properties of one or more VMs/containers"
+ "start:Start container as a service"
+ "stop:Stop container (equal to poweroff)"
+ "login:Get a login prompt on a VM/container"
+ "shell:Invoke a shell (or other command) in a container"
+ "enable:Enable automatic container start at boot"
+ "disable:Disable automatic container start at boot"
+ "poweroff:Power off one or more VMs/containers"
+ "reboot:Reboot one or more VMs/containers"
+ "terminate:Terminate one or more VMs/containers"
+ "kill:Send signal to process or a VM/container"
+ "copy-to:Copy files from the host to a container"
+ "copy-from:Copy files from a container to the host"
+ "bind:Bind mount a path from the host into a container"
+
+ "list-images:Show available container and VM images"
+ "image-status:Show image details"
+ "show-image:Show properties of image"
+ "edit:Edit settings of one or more VMs/containers"
+ "cat:Show settings of one or more VMs/containers"
+ "clone:Clone an image"
+ "rename:Rename an image"
+ "read-only:Mark or unmark image read-only"
+ "remove:Remove an image"
+ "set-limits:Set image or pool size limit (disk quota)"
+ "clean:Remove hidden (or all) images"
+
+ "pull-tar:Download a TAR container image"
+ "pull-raw:Download a RAW container or VM image"
+ "import-tar:Import a local TAR container image"
+ "import-raw:Import a local RAW container or VM image"
+ "import-fs:Import a local directory container image"
+ "export-tar:Export a TAR container image locally"
+ "export-raw:Export a RAW container or VM image locally"
+ "list-transfers:Show list of downloads in progress"
+ "cancel-transfer:Cancel a download"
+ )
+
+ if (( CURRENT == 1 )); then
+ _describe -t commands 'machinectl command' _machinectl_cmds || compadd "$@"
else
- _message "no more options"
+ local curcontext="$curcontext"
+ local stop=0
+ cmd="${${_machinectl_cmds[(r)$words[1]:*]%%:*}}"
+ case $cmd in
+ start|enable|disable)
+ _machinectl_images ;;
+
+ status|show|poweroff|reboot|terminate|kill)
+ _sd_machines ;;
+
+ login|shell)
+ if (( CURRENT == 2 )); then _sd_machines
+ else stop=1
+ fi ;;
+
+ copy-to|bind)
+ if (( CURRENT == 2 )); then _sd_machines
+ elif (( CURRENT == 3 )); then _files
+ elif (( CURRENT == 4 )); then _message "path on container"
+ else stop=1
+ fi ;;
+
+ copy-from)
+ if (( CURRENT == 2 )); then _sd_machines
+ elif (( CURRENT == 3 )); then _message "path on container"
+ elif (( CURRENT == 4 )); then _files
+ else stop=1
+ fi ;;
+
+ image-status|show-image|remove)
+ _machinectl_images ;;
+
+ edit|cat)
+ if (( CURRENT == 2 )); then _machinectl_images
+ else stop=1
+ fi ;;
+
+ clone|rename)
+ if (( CURRENT == 2 )); then _machinectl_images
+ elif (( CURRENT == 3 )); then _message "target image"
+ else stop=1
+ fi ;;
+
+ read-only)
+ if (( CURRENT == 2 )); then _machinectl_images
+ elif (( CURRENT == 3 )); then _values 'read-only flag' 'true' 'false'
+ else stop=1
+ fi ;;
+
+ set-limit)
+ if (( CURRENT == 2 )); then _machinectl_images
+ elif (( CURRENT == 3 )); then _message "size limit"
+ else stop=1
+ fi ;;
+
+ pull-tar|pull-raw)
+ if (( CURRENT == 2 )); then _message "${cmd#pull-} file URL"
+ elif (( CURRENT == 3 )); then _message "target image"
+ else stop=1
+ fi ;;
+
+ import-tar)
+ if (( CURRENT == 2 )); then _files -g "*.(tar(|.(gz|bz2|xz|zst))|tgz|tbz2|txz|tzst)(.)"
+ elif (( CURRENT == 3 )); then _message "target image"
+ else stop=1
+ fi ;;
+ import-raw)
+ if (( CURRENT == 2 )); then _files -g "*(.)"
+ elif (( CURRENT == 3 )); then _message "target image"
+ else stop=1
+ fi ;;
+ import-fs)
+ if (( CURRENT == 2 )); then _files -/
+ elif (( CURRENT == 3 )); then _message "target image"
+ else stop=1
+ fi ;;
+
+ export-tar|export-raw)
+ if (( CURRENT == 2 )); then _machinectl_images
+ elif (( CURRENT == 3 )); then _files
+ else stop=1
+ fi ;;
+
+ list*|clean|cancel-transfer)
+ stop=1 ;;
+
+ '')
+ stop=1 ;;
+ esac
+
+ if (( stop )); then
+ _message "no more options"
+ return 1
+ fi
fi
- fi
}
_arguments \
- {-h,--help}'[Prints a short help text and exits.]' \
- '--version[Prints a short version string and exits.]' \
- \*{-p,--property=}'[Limit output to specified property.]:property:(Name Id Timestamp TimestampMonotonic Service Scope Leader Class State RootDirectory)' \
- {-a,--all}'[Show all proerties]' \
- (-l,--full)'[Do not ellipsize cgroup members]' \
- '--no-pager[Do not pipe output into a pager]' \
- '--no-ask-password[Do not ask for system passwords]' \
- '--kill-who=[Who to send signal to]:killwho:(leader all)' \
- {-s,--signal=}'[Which signal to send]:signal:_signals' \
- {-H,--host=}'[Show information for remote host]:userathost:_sd_hosts_or_user_at_host' \
- {-P,--privileged}'[Acquire privileges before execution]' \
- '*::machinectl command:_machinectl_command'
+ '(- *)'{-h,--help}'[Prints a short help text and exits.]' \
+ '(- *)--version[Prints a short version string and exits.]' \
+ '--no-pager[Do not pipe output into a pager.]' \
+ '--no-legend[Do not show the headers and footers.]' \
+ '--no-ask-password[Do not ask for system passwords.]' \
+ '(-H --host)'{-H+,--host=}'[Operate on remote host.]:userathost:_sd_hosts_or_user_at_host' \
+ '(-M --machine)'{-M+,--machine=}'[Operate on local container.]:machine:_sd_machines' \
+ '(-p --property)'{-p+,--property=}'[Limit output to specified property.]:property:(Name Id Timestamp TimestampMonotonic Service Scope Leader Class State RootDirectory)' \
+ '(-a --all)'{-a,--all}'[Show all properties.]' \
+ '(-q --quiet)'{-q,--quiet}'[Suppress output.]' \
+ '(-l --full)'{-l,--full}'[Do not ellipsize cgroup members.]' \
+ '--kill-whom=[Whom to send signal to.]:killwhom:(leader all)' \
+ '(-s --signal)'{-s+,--signal=}'[Which signal to send.]:signal:_signals' \
+ '--read-only[Create read-only bind mount.]' \
+ '--mkdir[Create directory before bind mounting, if missing.]' \
+ '(-n --lines)'{-n+,--lines=}'[Number of journal entries to show.]:integer' \
+ '(-o --output)'{-o+,--output=}'[Change journal output mode.]:output modes:_sd_outputmodes' \
+ '--verify=[Verification mode for downloaded images.]:verify:(no checksum signature)' \
+ '--force[Download image even if already exists.]' \
+ '*::machinectl command:_machinectl_commands'