about summary refs log tree commit diff
path: root/Functions/Zftp/zfrglob
diff options
context:
space:
mode:
Diffstat (limited to 'Functions/Zftp/zfrglob')
-rw-r--r--Functions/Zftp/zfrglob70
1 files changed, 70 insertions, 0 deletions
diff --git a/Functions/Zftp/zfrglob b/Functions/Zftp/zfrglob
new file mode 100644
index 000000000..f9d67b3f2
--- /dev/null
+++ b/Functions/Zftp/zfrglob
@@ -0,0 +1,70 @@
+# function zfrglob {
+# Do the remote globbing for zfput, etc.
+# We have two choices:
+#  (1) Get the entire file list and match it one by one
+#      locally against the pattern.
+#      Causes problems if we are globbing directories (rare, presumably).
+#      But: we can cache the current directory, which
+#      we need for completion anyway.  Works on any OS if you
+#      stick with a single directory.  This is the default.
+#  (2) Use remote globbing, i.e. pass it to ls at the site.
+#      Faster, but only works with UNIX, and only basic globbing.
+#      We do this if $zfrglob is non-null.
+
+# There is only one argument, the variable containing the
+# pattern to be globbed.  We set this back to an array containing
+# all the matches.
+
+emulate -L zsh
+setopt extendedglob
+
+local pat dir nondir files i
+
+eval pat=\$$1
+
+# Check if we really need to do anything.  Look for standard
+# globbing characters, and if we are
+# using zsh for the actual pattern matching also look for
+# extendedglob characters.
+if [[ $pat != *[][*?]* &&
+  ( -n $zfrglob || $pat != *[(|)#^]* ) ]]; then
+  return 0
+fi
+local tmpf=${TMPPREFIX}zfrglob$$
+
+if [[ $zfrglob != '' ]]; then
+  zftp ls "$pat" >$tmpf 2>/dev/null
+  eval "$1=(\$(<\$tmpf))"
+  rm -f $tmpf
+else
+  if [[ $ZFTP_SYSTEM = UNIX* && $pat = */* ]]; then
+    # not the current directory and we know how to handle paths
+    if [[ $pat = ?*/* ]]; then
+      # careful not to remove too many slashes
+      dir=${pat%/*}
+    else
+      dir=/
+    fi
+    nondir=${pat##*/}
+    zftp ls "$dir" 2>/dev/null >$tmpf
+    files=($(<$tmpf))
+    files=(${files:t})
+    rm -f $tmpf
+  else
+    # we just have to do an ls and hope that's right
+    nondir=$pat
+    if (( $#zftp_fcache == 0 )); then
+      # Why does `zftp_fcache=($(zftp ls))' sometimes not work?
+      zftp ls >$tmpf
+      zftp_fcache=($(<$tmpf))
+      rm -f $tmpf
+    fi
+    files=($zftp_fcache)
+  fi
+  # now we want to see which of the $files match $nondir:
+  # ${...:/foo} deletes occurrences of foo matching a complete word,
+  # while the ^ inverts the sense so that anything not matching the
+  # pattern in $nondir is excluded.
+  eval "$1=(\${files:/^\${~nondir}})"
+fi
+# }