# cvs(1) completion -*- shell-script -*- proc _cvs_entries { local prefix=$(cur%/*)/ IFS=$'\n' [[ -e ${prefix:-}CVS/Entries ]] || setglobal prefix = ''"" setglobal entries = ''( $( cut -d/ -f2 -s ${prefix:-}CVS/Entries 2>/dev/null ) ) if [[ $entries ]] { setglobal entries = ''( "${entries[@]/#/${prefix:-}}" ) compopt -o filenames } } proc _cvs_modules { if [[ -n $prefix ]] { setglobal COMPREPLY = ''( $( command ls -d ${cvsroot}/${prefix}/!(CVSROOT) ) ) } else { setglobal COMPREPLY = ''( $( command ls -d ${cvsroot}/!(CVSROOT) ) ) } } proc _cvs_commands { cvs --help-commands !2 > !1 | awk '/^( *|\t)/ { print $1 }' } proc _cvs_command_options { setglobal COMPREPLY = ''( $( compgen -W '$( _parse_help "$1" "--help $2" )' -- "$cur" ) ) } proc _cvs_kflags { setglobal COMPREPLY = ''( $( compgen -W 'kv kvl k o b v' -- "$cur" ) ) } proc _cvs_roots { local -a cvsroots setglobal cvsroots = ''( $CVSROOT ) [[ -r ~/.cvspass ]] && setglobal cvsroots = ''( $( awk '{ print $2 }' ~/.cvspass ) ) [[ -r CVS/Root ]] && mapfile -tO $(#cvsroots[@]) cvsroots < CVS/Root setglobal COMPREPLY = ''( $( compgen -W '${cvsroots[@]}' -- "$cur" ) ) __ltrim_colon_completions $cur } proc _cvs { local cur prev words cword _init_completion -n : || return local count mode i cvsroot cvsroots pwd local -a flags files entries changed newremoved setglobal count = '0' for i in [$(words[@])] { [[ $count -eq $cword ]] && break # Last parameter was the CVSROOT, now go back to mode selection if [[ "${words[((count))]}" == "$cvsroot" && "$mode" == cvsroot ]] { setglobal mode = ''"" } if [[ -z $mode ]] { match $i { with -H|--help setglobal COMPREPLY = ''( $( compgen -W "$( _cvs_commands )" -- "$cur" ) ) return 0 with -d setglobal mode = 'cvsroot' setglobal cvsroot = $(words[((count+1))]) with add|ad|new setglobal mode = 'add' with admin|adm|rcs setglobal mode = 'admin' with annotate|ann|blame|rannotate|rann|ra setglobal mode = 'annotate' with checkout|co|get setglobal mode = 'checkout' with commit|ci|com setglobal mode = 'commit' with diff|di|dif setglobal mode = 'diff' with export|ex|exp setglobal mode = 'export' with edit|unedit|editors|logout|pserver|server|watch|watchers setglobal mode = $i with history|hi|his setglobal mode = 'history' with import|im|imp setglobal mode = 'import' with log|lo|rlog|rl setglobal mode = 'log' with login|logon|lgn setglobal mode = 'login' with rdiff|patch|pa setglobal mode = 'rdiff' with release|re|rel setglobal mode = 'release' with remove|rm|delete setglobal mode = 'remove' with rtag|rt|rfreeze setglobal mode = 'rtag' with status|st|stat setglobal mode = 'status' with tag|ta|freeze setglobal mode = 'tag' with update|up|upd setglobal mode = 'update' with version|ve|ver setglobal mode = 'version' } } elif [[ "$i" == -* ]] { setglobal flags = ''( $i ) } setglobal count = $shExpr('++count') } match $mode { with add match $prev { with -m return 0 with -k _cvs_kflags return 0 } if [[ "$cur" != -* ]] { _cvs_entries [[ -z $cur ]] && setglobal files = ''( !(CVS) ) || \ setglobal files = ''( $( command ls -d ${cur}* 2>/dev/null ) ) local f for i in [$(!files[@])] { if [[ ${files[i]} == ?(*/)CVS ]] { unset 'files[i]' } else { for f in [$(entries[@])] { if [[ ${files[i]} == $f && ! -d $f ]] { unset 'files[i]' break } } } } setglobal COMPREPLY = ''( $( compgen -X "$_backup_glob" -W '${files[@]}' \ -- "$cur" ) ) } else { _cvs_command_options $1 $mode } with admin match $prev { with -a|-A|-b|-c|-e|-l|-m|-n|-N|-o|-s|-t-|-u return 0 with -t _filedir return 0 with -k _cvs_kflags return 0 } if [[ "$cur" == -* ]] { _cvs_command_options $1 $mode } else { _cvs_entries setglobal COMPREPLY = ''( $( compgen -W '${entries[@]}' -- "$cur" ) ) } with annotate [[ "$prev" == -[rD] ]] && return 0 if [[ "$cur" == -* ]] { _cvs_command_options $1 $mode } else { _cvs_entries setglobal COMPREPLY = ''( $( compgen -W '${entries[@]}' -- "$cur" ) ) } with checkout match $prev { with -r|-D|-j return 0 with -d _filedir -d return 0 with -k _cvs_kflags return 0 } if [[ "$cur" != -* ]] { [[ -z $cvsroot ]] && setglobal cvsroot = $CVSROOT setglobal COMPREPLY = ''( $( cvs -d "$cvsroot" co -c 2> /dev/null | \ awk '{print $1}' ) ) setglobal COMPREPLY = ''( $( compgen -W '${COMPREPLY[@]}' -- "$cur" ) ) } else { _cvs_command_options $1 $mode } with commit match $prev { with -m|-r return 0 with -F _filedir return 0 } if [[ "$cur" != -* ]] { # if $COMP_CVS_REMOTE is not null, 'cvs commit' will # complete on remotely checked-out files (requires # passwordless access to the remote repository if [[ -n ${COMP_CVS_REMOTE:-} ]] { # this is the least computationally intensive way found so # far, but other changes (something other than # changed/removed/new) may be missing setglobal changed = ''( $( cvs -q diff --brief 2>&1 | \ sed -ne 's/^Files [^ ]* and \([^ ]*\) differ$/\1/p' ) ) setglobal newremoved = ''( $( cvs -q diff --brief 2>&1 | \ sed -ne 's/^cvs diff: \([^ ]*\) .*, no comparison available$/\1/p' ) ) setglobal COMPREPLY = ''( $( compgen -W '${changed[@]:-} \ ${newremoved[@]:-}' -- "$cur" ) ) } else { _cvs_entries setglobal COMPREPLY = ''( $( compgen -W '${entries[@]}' -- "$cur" ) ) } } else { _cvs_command_options $1 $mode } with cvsroot _cvs_roots with diff if [[ "$cur" == -* ]] { _cvs_command_options $1 $mode [[ $COMPREPLY == *= ]] && compopt -o nospace } else { _cvs_entries setglobal COMPREPLY = ''( $( compgen -W '${entries[@]:-}' -- "$cur" ) ) } with editors|watchers if [[ "$cur" == -* ]] { _cvs_command_options $1 $mode } else { _cvs_entries setglobal COMPREPLY = ''( $( compgen -W '${entries[@]}' -- "$cur" ) ) } with export match $prev { with -r|-D return 0 with -d _filedir -d return 0 with -k _cvs_kflags return 0 } if [[ "$cur" != -* ]] { [[ -z $cvsroot ]] && setglobal cvsroot = $CVSROOT setglobal COMPREPLY = ''( $( cvs -d "$cvsroot" co -c | awk '{print $1}' ) ) setglobal COMPREPLY = ''( $( compgen -W '${COMPREPLY[@]}' -- "$cur" ) ) } else { _cvs_command_options $1 $mode } with import match $prev { with -I|-b|-m|-W return 0 with -k _cvs_kflags return 0 } if [[ "$cur" != -* ]] { # starts with same algorithm as checkout [[ -z $cvsroot ]] && setglobal cvsroot = $CVSROOT local prefix=$(cur%/*) if [[ -r ${cvsroot}/${prefix} ]] { _cvs_modules setglobal COMPREPLY = ''( ${COMPREPLY[@]#$cvsroot} ) setglobal COMPREPLY = ''( ${COMPREPLY[@]#\/} ) } setglobal pwd = $[ pwd] setglobal pwd = $(pwd##*/) setglobal COMPREPLY = ''( $( compgen -W '${COMPREPLY[@]} $pwd' -- "$cur" ) ) } else { _cvs_command_options $1 $mode } with remove if [[ "$cur" != -* ]] { _cvs_entries if [[ "$prev" != -f ]] { # find out what files are missing for i in [$(!entries[@])] { [[ -r "${entries[i]}" ]] && unset 'entries[i]' } } setglobal COMPREPLY = ''( $( compgen -W '${entries[@]:-}' -- "$cur" ) ) } else { _cvs_command_options $1 $mode } with update match $prev { with -r|-D|-j|-I|-W return 0 with -k _cvs_kflags return 0 } if [[ "$cur" == -* ]] { _cvs_command_options $1 $mode } else { _cvs_entries setglobal COMPREPLY = ''( $( compgen -W '${entries[@]}' -- "$cur" ) ) } with "" match $prev { with -T _filedir -d return 0 with -e|-s return 0 with -z setglobal COMPREPLY = ''( $( compgen -W '{1..9}' -- "$cur" ) ) return 0 } setglobal COMPREPLY = ''( $( compgen -W '$( _cvs_commands ) $( _parse_help "$1" --help-options ) --help --help-commands --help-options --version' -- "$cur" ) ) } return 0 } && complete -F _cvs cvs # ex: ts=4 sw=4 et filetype=sh