Package: pristine-tar
Version: 1.44
Severity: minor

Dear Maintainer,

please consider proposed improvements for completion script. Completion
of --signature-file option, git refs and more!

For your convenience, I am attaching both series of git commit in mbox
format (suitable for git-am) and new version of script.
>From 4a2c798d5638c4ebeecc7e1a03ac7d52bbf47cd5 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Tue, 23 Oct 2018 19:06:41 +0000
Subject: [PATCH 1/9] Remove have() function from bash-completion

This function is not needed, since completion scripts are loaded
dynamically, on first use.

For more information, see /usr/share/bash-completion/bash_completion
---
 bash_completion/pristine-tar | 12 ------------
 1 file changed, 12 deletions(-)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index a0b7777..69c2a17 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -1,14 +1,3 @@
-
-have()
-{
-    unset -v have
-    # Completions for system administrator commands are installed as well in
-    # case completion is attempted via `sudo command ...'.
-    PATH=$PATH:/sbin:/usr/sbin:/usr/local/sbin type $1 &>/dev/null &&
-    have="yes"
-}
-
-have pristine-tar && 
 _pristine_tar()
 {
   COMPREPLY=()
@@ -33,5 +22,4 @@ _pristine_tar()
 } &&
 complete -F _pristine_tar pristine-tar
 
-unset -f have
 # vim: ft=sh

>From f1d3b695db7c64624596b8c4ba2aa73ac5dff02a Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 00:05:03 +0000
Subject: [PATCH 2/9] Complete long versions of options

Long versions are much more useful, since they are self-explanatory.
Completing short options saves little to no typing, and provides little
information to user, who do not already know what option they need.
---
 bash_completion/pristine-tar | 11 ++++++++++-
 1 file changed, 10 insertions(+), 1 deletion(-)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index 69c2a17..1805c1a 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -1,12 +1,21 @@
 _pristine_tar()
 {
+  local options='
+    --verbose
+    --debug
+    --message
+    --signature-file
+    --recompress
+    --recompress-threhold-bytes
+    --recompress-threhold-percent
+  '
   COMPREPLY=()
   _get_comp_words_by_ref -n : cur prev
   #cur=`_get_cword :`
   #prev=`_get_pword`
 
   if [[ "$cur" == -* ]]; then
-    COMPREPLY=( $( compgen -W '-v -d -f' -- "$cur" ) )
+    COMPREPLY=( $( compgen -W "${options}" -- "$cur" ) )
     return 0
   fi
 

>From 9da80d0ab0e8bcf36055a20bed64ab62ad52f152 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 00:22:16 +0000
Subject: [PATCH 3/9] Make bash completion more robust

Test, whether we are completing subcommands by checking
$COMP_CWORD index, not previous word.
---
 bash_completion/pristine-tar | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index 1805c1a..48e9b4a 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -19,7 +19,7 @@ _pristine_tar()
     return 0
   fi
 
-  if [[ "$prev" == 'pristine-tar' ]]; then
+  if [[ "${COMP_CWORD}" = 1 ]]; then
     COMPREPLY=( $( compgen -W 'gendelta gentar commit checkout verify list' -- 
"$cur" ))
     return 0
   fi

>From 5eb983690b3cb0aca24f42fe11293da255e64cdc Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 00:42:41 +0000
Subject: [PATCH 4/9] Keep bash-completion script ad 80 column limit

Factor list of sub-commands to separate local variable to make script
source to not exceed 80 column.
---
 bash_completion/pristine-tar | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index 48e9b4a..26e2384 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -9,6 +9,14 @@ _pristine_tar()
     --recompress-threhold-bytes
     --recompress-threhold-percent
   '
+  local subcommands='
+    gendelta
+    gentar
+    commit
+    checkout
+    verify
+    list
+  '
   COMPREPLY=()
   _get_comp_words_by_ref -n : cur prev
   #cur=`_get_cword :`
@@ -20,7 +28,7 @@ _pristine_tar()
   fi
 
   if [[ "${COMP_CWORD}" = 1 ]]; then
-    COMPREPLY=( $( compgen -W 'gendelta gentar commit checkout verify list' -- 
"$cur" ))
+    COMPREPLY=( $( compgen -W "${subcommands}" -- "$cur" ))
     return 0
   fi
 

>From 4b01a5589184fa667d271033f83d9f2ec1240062 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 01:09:41 +0000
Subject: [PATCH 5/9] Improve handling f non-completeable options

---
 bash_completion/pristine-tar | 6 ++++++
 1 file changed, 6 insertions(+)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index 26e2384..f79fd2a 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -32,6 +32,12 @@ _pristine_tar()
     return 0
   fi
 
+  case "${prev}" in
+    (-m|--message) return 0 ;;
+    (-B|--recompress-threhold-bytes) return 0 ;;
+    (-P|--recompress-threhold-percent) return 0 ;;
+  esac
+
   # else, complete with tarball names that pristine-tar knows about
   dirname=$(dirname "$cur")
   COMPREPLY=( $(compgen -W "$(git ls-tree --name-only pristine-tar 2>/dev/null 
| sed '/\.id$/!d; s/\.id$//' | xargs -n 1 printf "$dirname/%s\n")" -- "$cur" ) )

>From c111067f2ee16e4f219c4f5d3d6f42a5b2775c32 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 03:04:19 +0000
Subject: [PATCH 6/9] Implement completion for --signature-file option

---
 bash_completion/pristine-tar | 33 +++++++++++++++++++++++++++++++++
 1 file changed, 33 insertions(+)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index f79fd2a..0cc585f 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -1,3 +1,24 @@
+# ${cur} must be provided by caller
+_pristine_tar_sigfile () {
+  local dirname="${cur%/*}"
+  if [[ "${dirname}" == "${cur}" ]] ; then
+    dirname=''
+  fi
+
+  # As far as I can observe (without digging into sources), there are
+  # only three possible extensions of files -- .id .asc .delta
+  # -- Dmitry Bogatov <[email protected]> Wed, 24 Oct 2018 02:53:18 +0000
+  local possibilities=''
+  for name in $(git ls-tree --name-only pristine-tar) ; do
+    [[ "${name##*.}" = asc ]] || continue # we need only .asc files
+    if [[ "${dirname}" ]] ; then
+      name="${dirname}/${name}"
+    fi
+    possibilities="${possibilities} ${name}"
+  done
+  COMPREPLY+=( $(compgen -W "${possibilities}" -- "${cur}") )
+}
+
 _pristine_tar()
 {
   local options='
@@ -32,10 +53,22 @@ _pristine_tar()
     return 0
   fi
 
+  # Sub-command 'checkout' is special -- its argument specify something
+  # (either tarball or signature) already stored on pristine-tar branch.
+  local subcommand="${COMP_WORDS[1]}"
   case "${prev}" in
     (-m|--message) return 0 ;;
     (-B|--recompress-threhold-bytes) return 0 ;;
     (-P|--recompress-threhold-percent) return 0 ;;
+    (-s|--signature-file)
+      if [[ "${subcommand}" = 'checkout' ]] ; then
+        _pristine_tar_sigfile
+      else
+        for e in asc gpg pgp sig ; do
+          _filedir "${e}"
+        done
+      fi
+      return 0
   esac
 
   # else, complete with tarball names that pristine-tar knows about

>From 87474624e28e31a3b21cbc1e270f5d9f6f0aafd6 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 03:23:29 +0000
Subject: [PATCH 7/9] Write tar file completion, with 'checkout' special case

---
 bash_completion/pristine-tar | 18 +++++++++++-------
 1 file changed, 11 insertions(+), 7 deletions(-)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index 0cc585f..487face 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -1,5 +1,6 @@
 # ${cur} must be provided by caller
-_pristine_tar_sigfile () {
+_pristine_tar_listing () {
+  local kind="${1}" # either 'asc' or 'id'
   local dirname="${cur%/*}"
   if [[ "${dirname}" == "${cur}" ]] ; then
     dirname=''
@@ -10,7 +11,9 @@ _pristine_tar_sigfile () {
   # -- Dmitry Bogatov <[email protected]> Wed, 24 Oct 2018 02:53:18 +0000
   local possibilities=''
   for name in $(git ls-tree --name-only pristine-tar) ; do
-    [[ "${name##*.}" = asc ]] || continue # we need only .asc files
+    [[ "${name##*.}" = "${kind}" ]] || continue
+    [[ "${kind}" = 'id' ]] && name="${name%.id}"
+
     if [[ "${dirname}" ]] ; then
       name="${dirname}/${name}"
     fi
@@ -62,7 +65,7 @@ _pristine_tar()
     (-P|--recompress-threhold-percent) return 0 ;;
     (-s|--signature-file)
       if [[ "${subcommand}" = 'checkout' ]] ; then
-        _pristine_tar_sigfile
+        _pristine_tar_listing 'asc'
       else
         for e in asc gpg pgp sig ; do
           _filedir "${e}"
@@ -71,10 +74,11 @@ _pristine_tar()
       return 0
   esac
 
-  # else, complete with tarball names that pristine-tar knows about
-  dirname=$(dirname "$cur")
-  COMPREPLY=( $(compgen -W "$(git ls-tree --name-only pristine-tar 2>/dev/null 
| sed '/\.id$/!d; s/\.id$//' | xargs -n 1 printf "$dirname/%s\n")" -- "$cur" ) )
-
+  if [[ "${subcommand}" = 'checkout' ]] ; then
+    _pristine_tar_listing 'id'
+  else
+    _filedir
+  fi
 } &&
 complete -F _pristine_tar pristine-tar
 

>From d870335a28e1dcda3cfab15fbce61f3dd1aa7573 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 03:48:02 +0000
Subject: [PATCH 8/9] Fix  completion for 'checkout' command

Fix issue, that caused missing completion with trying to checkout
archive directly under /.
---
 bash_completion/pristine-tar | 13 +++++++------
 1 file changed, 7 insertions(+), 6 deletions(-)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index 487face..cfc0dd2 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -2,9 +2,10 @@
 _pristine_tar_listing () {
   local kind="${1}" # either 'asc' or 'id'
   local dirname="${cur%/*}"
-  if [[ "${dirname}" == "${cur}" ]] ; then
-    dirname=''
-  fi
+  local within_root=no
+
+  [[ "${cur:0:1}" = '/' && ! "${dirname}" ]] && within_root=yes
+  [[ "${dirname}" = "${cur}" ]] && dirname=''
 
   # As far as I can observe (without digging into sources), there are
   # only three possible extensions of files -- .id .asc .delta
@@ -14,9 +15,9 @@ _pristine_tar_listing () {
     [[ "${name##*.}" = "${kind}" ]] || continue
     [[ "${kind}" = 'id' ]] && name="${name%.id}"
 
-    if [[ "${dirname}" ]] ; then
-      name="${dirname}/${name}"
-    fi
+    [[ "${dirname}" ]] && name="${dirname}/${name}"
+    [[ "${within_root}" = yes ]] && name="/${name}"
+
     possibilities="${possibilities} ${name}"
   done
   COMPREPLY+=( $(compgen -W "${possibilities}" -- "${cur}") )

>From ab219520891e5b5d0a77c050f4cdc3dee176f986 Mon Sep 17 00:00:00 2001
From: Dmitry Bogatov <[email protected]>
Date: Wed, 24 Oct 2018 04:19:50 +0000
Subject: [PATCH 9/9] Add completion of git refs for 'commit' subcommand

---
 bash_completion/pristine-tar | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/bash_completion/pristine-tar b/bash_completion/pristine-tar
index cfc0dd2..21e952e 100644
--- a/bash_completion/pristine-tar
+++ b/bash_completion/pristine-tar
@@ -77,6 +77,14 @@ _pristine_tar()
 
   if [[ "${subcommand}" = 'checkout' ]] ; then
     _pristine_tar_listing 'id'
+  elif [[ "${subcommand}" = 'commit' && "${cur}" = refs/* ]] ; then
+    # 'commit' sub-command has two positional arguments, which has
+    # vastly diffent meaning. First one is filename, and second one is
+    # Git ref. Finding out, which one we are completing is rather
+    # complicated, so instead strings starting with 'refs/' are
+    # completed as Git references, and as filenames otherwise.
+    local references="$(git show-ref | cut -d' ' -f2)"
+    COMPREPLY+=( $(compgen -W "${references}" -- "${cur}") )
   else
     _filedir
   fi
# ${cur} must be provided by caller
_pristine_tar_listing () {
  local kind="${1}" # either 'asc' or 'id'
  local dirname="${cur%/*}"
  local within_root=no

  [[ "${cur:0:1}" = '/' && ! "${dirname}" ]] && within_root=yes
  [[ "${dirname}" = "${cur}" ]] && dirname=''

  # As far as I can observe (without digging into sources), there are
  # only three possible extensions of files -- .id .asc .delta
  # -- Dmitry Bogatov <[email protected]> Wed, 24 Oct 2018 02:53:18 +0000
  local possibilities=''
  for name in $(git ls-tree --name-only pristine-tar) ; do
    [[ "${name##*.}" = "${kind}" ]] || continue
    [[ "${kind}" = 'id' ]] && name="${name%.id}"

    [[ "${dirname}" ]] && name="${dirname}/${name}"
    [[ "${within_root}" = yes ]] && name="/${name}"

    possibilities="${possibilities} ${name}"
  done
  COMPREPLY+=( $(compgen -W "${possibilities}" -- "${cur}") )
}

_pristine_tar()
{
  local options='
    --verbose
    --debug
    --message
    --signature-file
    --recompress
    --recompress-threhold-bytes
    --recompress-threhold-percent
  '
  local subcommands='
    gendelta
    gentar
    commit
    checkout
    verify
    list
  '
  COMPREPLY=()
  _get_comp_words_by_ref -n : cur prev
  #cur=`_get_cword :`
  #prev=`_get_pword`

  if [[ "$cur" == -* ]]; then
    COMPREPLY=( $( compgen -W "${options}" -- "$cur" ) )
    return 0
  fi

  if [[ "${COMP_CWORD}" = 1 ]]; then
    COMPREPLY=( $( compgen -W "${subcommands}" -- "$cur" ))
    return 0
  fi

  # Sub-command 'checkout' is special -- its argument specify something
  # (either tarball or signature) already stored on pristine-tar branch.
  local subcommand="${COMP_WORDS[1]}"
  case "${prev}" in
    (-m|--message) return 0 ;;
    (-B|--recompress-threhold-bytes) return 0 ;;
    (-P|--recompress-threhold-percent) return 0 ;;
    (-s|--signature-file)
      if [[ "${subcommand}" = 'checkout' ]] ; then
        _pristine_tar_listing 'asc'
      else
        for e in asc gpg pgp sig ; do
          _filedir "${e}"
        done
      fi
      return 0
  esac

  if [[ "${subcommand}" = 'checkout' ]] ; then
    _pristine_tar_listing 'id'
  elif [[ "${subcommand}" = 'commit' && "${cur}" = refs/* ]] ; then
    # 'commit' sub-command has two positional arguments, which has
    # vastly diffent meaning. First one is filename, and second one is
    # Git ref. Finding out, which one we are completing is rather
    # complicated, so instead strings starting with 'refs/' are
    # completed as Git references, and as filenames otherwise.
    local references="$(git show-ref | cut -d' ' -f2)"
    COMPREPLY+=( $(compgen -W "${references}" -- "${cur}") )
  else
    _filedir
  fi
} &&
complete -F _pristine_tar pristine-tar

# vim: ft=sh

Reply via email to