Skip to content

Commit fe46238

Browse files
committed
refactor(scp): factorize common codes
1 parent 7aeb047 commit fe46238

File tree

1 file changed

+42
-26
lines changed

1 file changed

+42
-26
lines changed

completions/ssh

Lines changed: 42 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -461,6 +461,41 @@ _comp_cmd_sftp()
461461
# things we want to backslash escape in scp paths
462462
_comp_cmd_scp__path_esc='[][(){}<>"'"'"',:;^&!$=?`\\|[:space:]]'
463463

464+
# Escape shell special characters in filenames by backslash. This also
465+
# suffixes a space or a slash based on the file type.
466+
#
467+
# Note: With a non-empty prefix ($1 of _comp_xfunc_scp_compgen_local_files),
468+
# Bash will not recognize any filenames, so we need to perform the proper
469+
# quoting manually. We also need to manually suffix a space or a slash based
470+
# on the file type because "-o nospace" is specified. One might think of using
471+
# "compopt +o nospace" instead, but it would suffix a space to directory names
472+
# unexpectedly.
473+
#
474+
# @param $1 dirs_only - If a non-empty value is specified, only directory names
475+
# are selected.
476+
# @param $2 escape_replacement - If a non-empty value is specified, special
477+
# characters are replaced with the specified value (instead of the default
478+
# '\\&').
479+
# @stdin - List of filenames in the "ls -1F" format, where filenames are
480+
# separated by newlines, and characters /=@|* are suffixed based on the types
481+
# of the files.
482+
_comp_cmd_scp__escape_path()
483+
{
484+
local dirs_only=$1 escape_replacement=${2:-'\\&'}
485+
if [[ $dirs_only ]]; then
486+
# escape problematic characters; remove non-dirs
487+
command sed \
488+
-e 's/'"$_comp_cmd_scp__path_esc"'/'"$escape_replacement"'/g' \
489+
-e '/[^/]$/d'
490+
else
491+
# escape problematic characters; remove executables, aliases, pipes
492+
# and sockets; add space at end of file names
493+
command sed \
494+
-e 's/'"$_comp_cmd_scp__path_esc"'/'"$escape_replacement"'/g' \
495+
-e 's/[*@]$//g' -e 's/\\[|=]$//g' -e 's/[^/]$/& /g'
496+
fi
497+
}
498+
464499
# Complete remote files with ssh. Returns paths escaped with three backslashes
465500
# (unless -l option is provided).
466501
# Options:
@@ -505,19 +540,9 @@ _comp_xfunc_scp_compgen_remote_files()
505540
fi
506541

507542
local _files
508-
if [[ $_dirs_only ]]; then
509-
# escape problematic characters; remove non-dirs
510-
_files=$(ssh -o 'Batchmode yes' "$_userhost" \
511-
command ls -aF1dL "$_path*" 2>/dev/null |
512-
command sed -e 's/'"$_comp_cmd_scp__path_esc"'/'"$_escape_replacement"'/g' -e '/[^/]$/d')
513-
else
514-
# escape problematic characters; remove executables, aliases, pipes
515-
# and sockets; add space at end of file names
516-
_files=$(ssh -o 'Batchmode yes' "$_userhost" \
517-
command ls -aF1dL "$_path*" 2>/dev/null |
518-
command sed -e 's/'"$_comp_cmd_scp__path_esc"'/'"$_escape_replacement"'/g' \
519-
-e 's/[*@]$//g' -e 's/\\[|=]$//g' -e 's/[^/]$/& /g')
520-
fi
543+
_files=$(ssh -o 'Batchmode yes' "$_userhost" \
544+
command ls -aF1dL "$_path*" 2>/dev/null |
545+
_comp_cmd_scp__escape_path "$_dirs_only" "$_escape_replacement")
521546
_comp_compgen -R split -l -- "$_files"
522547
}
523548

@@ -542,19 +567,10 @@ _comp_xfunc_scp_compgen_local_files()
542567

543568
local files
544569
_comp_expand_glob files '"$cur"*' || return 0
545-
if [[ $_dirsonly ]]; then
546-
_comp_compgen -RU files split -l ${1:+-P "$1"} -- "$(
547-
command ls -aF1dL "${files[@]}" 2>/dev/null |
548-
command sed -e "s/$_comp_cmd_scp__path_esc/\\\\&/g" \
549-
-e '/[^/]$/d'
550-
)"
551-
else
552-
_comp_compgen -RU files split -l ${1:+-P "$1"} -- "$(
553-
command ls -aF1dL "${files[@]}" 2>/dev/null |
554-
command sed -e "s/$_comp_cmd_scp__path_esc/\\\\&/g" \
555-
-e 's/[*@]$//g' -e 's/\\[|=]$//g' -e 's/[^/]$/& /g'
556-
)"
557-
fi
570+
_comp_compgen -RU files split -l ${1:+-P "$1"} -- "$(
571+
command ls -aF1dL "${files[@]}" 2>/dev/null |
572+
_comp_cmd_scp__escape_path "$_dirsonly"
573+
)"
558574
}
559575

560576
# @deprecated 2.12

0 commit comments

Comments
 (0)