diff --git a/tests/ices.zunit b/tests/ices.zunit index 9b1ac80be..6a15c488e 100755 --- a/tests/ices.zunit +++ b/tests/ices.zunit @@ -34,32 +34,37 @@ assert "$ZPLUGINS/test---atclone/readme.md" not_exists } @test 'make' { - run zinit as"null" id-as"test/make" atclone"printf 'all:\n\ttouch whatever\n' > Makefile" make"all" for zdharma-continuum/null + run zinit as"null" id-as"test/make" atclone"printf 'all:\n\ttouch whatever\n' > Makefile" make"" for zdharma-continuum/null assert $state equals 0 assert "$ZPLUGINS/test---make/whatever" is_file } @test 'completions' { - run zinit as"null" id-as"test/completions" atclone"touch _whatever" completions for zdharma-continuum/null + run zinit as"null" id-as"test/completions" atclone"echo '#compdef whatever' >| _whatever" completions for zdharma-continuum/null assert $state equals 0 assert "$ZPLUGINS/test---completions/_whatever" is_file assert "$ZINIT[COMPLETIONS_DIR]/_whatever" is_file + run zinit completions } @test 'completions-overwrite' { # if both are given, the completions wins - run zinit as"null" id-as"test/completions-overwrite" atclone"touch _whatever2" nocompletions completions for zdharma-continuum/null + run zinit as"null" id-as"test/completions-overwrite" atclone"echo '#compdef whatever2' >| _whatever2" nocompletions completions for zdharma-continuum/null assert $state equals 0 assert "$ZPLUGINS/test---completions-overwrite/_whatever2" is_file assert "$ZINIT[COMPLETIONS_DIR]/_whatever2" is_file + run zinit completions } @test 'completions-ignored' { # only the _valid file should be installed as a completion - run zinit as"null" id-as"test/ignored_completions" atclone"touch __init__.py _valid" completions for zdharma-continuum/null + run zinit as"null" id-as"test/ignored_completions" atclone"touch __init__.py; echo '#compdef valid' >| _valid" completions for zdharma-continuum/null assert $state equals 0 assert "$ZPLUGINS/test---ignored_completions/_valid" is_file assert "$ZPLUGINS/test---ignored_completions/__init__.py" is_file assert "$ZINIT[COMPLETIONS_DIR]/_valid" is_file COMPS=( "$ZINIT[COMPLETIONS_DIR]"/_* ) assert __init__.py is_not_value_in $COMPS + zinit delete --yes test/ignored_completions + run zinit cuninstall test/ignored_completions + assert $output contains 'No completions found for `test/ignored_completions' } # vim:ft=zsh:sw=2:sts=2:et:foldmarker=\ {,}:foldmethod=marker diff --git a/zinit-install.zsh b/zinit-install.zsh index 7912584ef..7ab6ff159 100644 --- a/zinit-install.zsh +++ b/zinit-install.zsh @@ -528,64 +528,62 @@ builtin source "${ZINIT[BIN_DIR]}/zinit-side.zsh" || { # $1 - plugin spec (4 formats: user---plugin, user/plugin, user, plugin) # $2 - plugin if $1 (i.e., user) given # $3 - if 1, then reinstall, otherwise only install completions that are not present -.zinit-install-completions() { +.zinit-install-completions () { builtin emulate -LR zsh ${=${options[xtrace]:#off}:+-o xtrace} - setopt nullglob extendedglob warncreateglobal typesetsilent noshortloops + setopt extended_glob no_short_loops null_glob typeset_silent warn_create_global + + local id_as=$1${2:+${${${(M)1:#%}:+$2}:-/$2}} + local reinstall=${3:-0} quiet=${${4:+1}:-0} + + (( OPTS[opt_-q,--quiet] )) && quiet=1 + [[ $4 = -Q ]] && quiet=2 - local id_as=$1${2:+${${${(M)1:#%}:+$2}:-/$2}} - local reinstall=${3:-0} quiet=${${4:+1}:-0} - (( OPTS[opt_-q,--quiet] )) && quiet=1 - [[ $4 = -Q ]] && quiet=2 typeset -ga INSTALLED_COMPS SKIPPED_COMPS - INSTALLED_COMPS=() SKIPPED_COMPS=() + INSTALLED_COMPS=() SKIPPED_COMPS=() .zinit-any-to-user-plugin "$id_as" "" - local user=${reply[-2]} - local plugin=${reply[-1]} + local user=${reply[-2]} + local plugin=${reply[-1]} .zinit-any-colorify-as-uspl2 "$user" "$plugin" - local abbrev_pspec=$REPLY - + local abbrev_pspec=$REPLY .zinit-exists-physically-message "$id_as" "" || return 1 - - # Symlink any completion files included in the plugin directory typeset -a completions already_symlinked backup_comps local c cfile bkpfile - # The plugin == . is a semi-hack/trick to handle 'creinstall .' properly - [[ $user == % || ( -z $user && $plugin == . ) ]] && \ - completions=( "${plugin}"/**/_[^_.]*~*(*.zwc|*.html|*.txt|*.png|*.jpg|*.jpeg|*.js|*.md|*.yml|*.yaml|*.py|*.ri|_zsh_highlight*|/zsdoc/*|*.ps1)(DN^/) ) || \ - completions=( "${ZINIT[PLUGINS_DIR]}/${id_as//\//---}"/**/_[^_.]*~*(*.zwc|*.html|*.txt|*.png|*.jpg|*.jpeg|*.js|*.md|*.yml|*.yaml|*.py|*.ri|_zsh_highlight*|/zsdoc/*|*.ps1)(DN^/) ) - already_symlinked=( "${ZINIT[COMPLETIONS_DIR]}"/_[^_.]*~*.zwc(DN) ) - backup_comps=( "${ZINIT[COMPLETIONS_DIR]}"/[^_.]*~*.zwc(DN) ) - + nt () { + [[ $(head -n 1 $REPLY) != *compdef* ]] + } + # Symlink any completion files included in the plugin directory + [[ $user == % || ( -z $user && $plugin == . ) ]] && completions=("${plugin}"/**/(_*|*zsh*)(DN^/+nt)) || completions=("${ZINIT[PLUGINS_DIR]}/${id_as//\//---}"/**/(_*|*.zsh*)(DN^/+nt)) + already_symlinked=("${ZINIT[COMPLETIONS_DIR]}"/_[^_.]*~*.zwc(DN)) + backup_comps=("${ZINIT[COMPLETIONS_DIR]}"/[^_.]*~*.zwc(DN)) # Symlink completions if they are not already there # either as completions (_fname) or as backups (fname) # OR - if its a reinstall for c in "${completions[@]:A}"; do - cfile="${c:t}" - bkpfile="${cfile#_}" - if [[ ( -z ${already_symlinked[(r)*/$cfile]} || $reinstall = 1 ) && - -z ${backup_comps[(r)*/$bkpfile]} - ]]; then + cfile="${c:t}" + if [[ $cfile != (#s)_* ]]; then + cfile="_${${$(head -n1 ${c})//\#compdef/}// /}" + +zi-log "{m} _${${$(head -n1 ${c})//\#compdef/}// /}" + fi + bkpfile="${cfile#_}" + if [[ ( -z ${already_symlinked[(r)*/$cfile]} || $reinstall = 1 ) && -z ${backup_comps[(r)*/$bkpfile]} ]]; then if [[ $reinstall = 1 ]]; then - # Remove old files command rm -f "${ZINIT[COMPLETIONS_DIR]}/$cfile" "${ZINIT[COMPLETIONS_DIR]}/$bkpfile" fi - INSTALLED_COMPS+=( $cfile ) + INSTALLED_COMPS+=($cfile) (( quiet )) || builtin print -Pr "Symlinking completion ${ZINIT[col-uname]}$cfile%f%b to completions directory." command ln -fs "$c" "${ZINIT[COMPLETIONS_DIR]}/$cfile" - # Make compinit notice the change .zinit-forget-completion "$cfile" "$quiet" else - SKIPPED_COMPS+=( $cfile ) + SKIPPED_COMPS+=($cfile) (( quiet )) || builtin print -Pr "Not symlinking completion \`${ZINIT[col-obj]}$cfile%f%b', it already exists." (( quiet )) || builtin print -Pr "${ZINIT[col-info2]}Use \`${ZINIT[col-pname]}zinit creinstall $abbrev_pspec${ZINIT[col-info2]}' to force install.%f%b" fi done - local comps msg - local -A comp_types=(\$INSTALLED_COMPS 'Installed' \$SKIPPED_COMPS 'Skipped re-installing') + local -A comp_types=(\$INSTALLED_COMPS 'Installed' \$SKIPPED_COMPS 'Skipped re-installing') for comps msg in ${(kv)comp_types}; do - local comps_num=${#${(e)comps}} + local comps_num=${#${(e)comps}} if (( comps_num > 0 )); then +zi-log "{m} ${msg} {num}$comps_num{rst} completion${=${comps_num:#1}:+s}" if (( quiet == 0 )); then @@ -593,13 +591,11 @@ builtin source "${ZINIT[BIN_DIR]}/zinit-side.zsh" || { fi fi done - - if (( ZSH_SUBSHELL )) { - builtin print -rl -- $INSTALLED_COMPS >! ${TMPDIR:-/tmp}/zinit.installed_comps.$$.lst - builtin print -rl -- $SKIPPED_COMPS >! ${TMPDIR:-/tmp}/zinit.skipped_comps.$$.lst - } - - .zinit-compinit 1 1 &>/dev/null + if (( ZSH_SUBSHELL )); then + builtin print -rl -- $INSTALLED_COMPS >| ${TMPDIR:-/tmp}/zinit.installed_comps.$$.lst + builtin print -rl -- $SKIPPED_COMPS >| ${TMPDIR:-/tmp}/zinit.skipped_comps.$$.lst + fi + .zinit-compinit 1 1 &> /dev/null } # ]]] # FUNCTION: .zinit-compinit [[[ # User-exposed `compinit' frontend which first ensures that all