* [TG RFC PATCH] Add bash completion script for TopGit
@ 2008-09-25 11:06 Jonas Fonseca
2008-09-25 13:47 ` [TG PATCH] Complete depend subcommand Jonas Fonseca
0 siblings, 1 reply; 2+ messages in thread
From: Jonas Fonseca @ 2008-09-25 11:06 UTC (permalink / raw)
To: Petr Baudis, git
The script is based on git's bash completion script.
Signed-off-by: Jonas Fonseca <fonseca@diku.dk>
---
contrib/tg-completion.bash | 438 ++++++++++++++++++++++++++++++++++++++++++++
3 files changed, 438 insertions(+), 0 deletions(-)
create mode 100755 contrib/tg-completion.bash
I have RFC'd this because I am still a topgit noob.
diff --git a/contrib/tg-completion.bash b/contrib/tg-completion.bash
new file mode 100755
index 0000000..35eabe9
--- /dev/null
+++ b/contrib/tg-completion.bash
@@ -0,0 +1,438 @@
+#
+# bash completion support for TopGit.
+#
+# Copyright (C) 2008 Jonas Fonseca <fonseca@diku.dk>
+# Copyright (C) 2006,2007 Shawn O. Pearce <spearce@spearce.org>
+# Based git's git-completion.sh: http://repo.or.cz/w/git/fastimport.git
+# Conceptually based on gitcompletion (http://gitweb.hawaga.org.uk/).
+# Distributed under the GNU General Public License, version 2.0.
+#
+# The contained completion routines provide support for completing:
+#
+# *) local and remote branch names
+# *) local and remote tag names
+# *) .git/remotes file names
+# *) git 'subcommands'
+# *) tree paths within 'ref:path/to/file' expressions
+# *) common --long-options
+#
+# To use these routines:
+#
+# 1) Copy this file to somewhere (e.g. ~/.git-completion.sh).
+# 2) Added the following line to your .bashrc:
+# source ~/.git-completion.sh
+#
+# 3) You may want to make sure the git executable is available
+# in your PATH before this script is sourced, as some caching
+# is performed while the script loads. If git isn't found
+# at source time then all lookups will be done on demand,
+# which may be slightly slower.
+#
+# 4) Consider changing your PS1 to also show the current branch:
+# PS1='[\u@\h \W$(__tg_ps1 " (%s)")]\$ '
+#
+# The argument to __tg_ps1 will be displayed only if you
+# are currently in a git repository. The %s token will be
+
+case "$COMP_WORDBREAKS" in
+*:*) : great ;;
+*) COMP_WORDBREAKS="$COMP_WORDBREAKS:"
+esac
+
+### {{{ Utilities
+
+__tgdir ()
+{
+ if [ -z "$1" ]; then
+ if [ -n "$__tg_dir" ]; then
+ echo "$__tg_dir"
+ elif [ -d .git ]; then
+ echo .git
+ else
+ git rev-parse --git-dir 2>/dev/null
+ fi
+ elif [ -d "$1/.git" ]; then
+ echo "$1/.git"
+ else
+ echo "$1"
+ fi
+}
+
+__tgcomp_1 ()
+{
+ local c IFS=' '$'\t'$'\n'
+ for c in $1; do
+ case "$c$2" in
+ --*=*) printf %s$'\n' "$c$2" ;;
+ *.) printf %s$'\n' "$c$2" ;;
+ *) printf %s$'\n' "$c$2 " ;;
+ esac
+ done
+}
+
+__tgcomp ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+ if [ $# -gt 2 ]; then
+ cur="$3"
+ fi
+ case "$cur" in
+ --*=)
+ COMPREPLY=()
+ ;;
+ *)
+ local IFS=$'\n'
+ COMPREPLY=($(compgen -P "$2" \
+ -W "$(__tgcomp_1 "$1" "$4")" \
+ -- "$cur"))
+ ;;
+ esac
+}
+
+__tg_heads ()
+{
+ local cmd i is_hash=y dir="$(__tgdir "$1")"
+ if [ -d "$dir" ]; then
+ git --git-dir="$dir" for-each-ref --format='%(refname:short)' \
+ refs/heads
+ return
+ fi
+ for i in $(git ls-remote "$1" 2>/dev/null); do
+ case "$is_hash,$i" in
+ y,*) is_hash=n ;;
+ n,*^{}) is_hash=y ;;
+ n,refs/heads/*) is_hash=y; echo "${i#refs/heads/}" ;;
+ n,*) is_hash=y; echo "$i" ;;
+ esac
+ done
+}
+
+__tg_refs ()
+{
+ local cmd i is_hash=y dir="$(__tgdir "$1")"
+ if [ -d "$dir" ]; then
+ if [ -e "$dir/HEAD" ]; then echo HEAD; fi
+ git --git-dir="$dir" for-each-ref --format='%(refname:short)' \
+ refs/tags refs/heads refs/remotes
+ return
+ fi
+ for i in $(git ls-remote "$dir" 2>/dev/null); do
+ case "$is_hash,$i" in
+ y,*) is_hash=n ;;
+ n,*^{}) is_hash=y ;;
+ n,refs/tags/*) is_hash=y; echo "${i#refs/tags/}" ;;
+ n,refs/heads/*) is_hash=y; echo "${i#refs/heads/}" ;;
+ n,refs/remotes/*) is_hash=y; echo "${i#refs/remotes/}" ;;
+ n,*) is_hash=y; echo "$i" ;;
+ esac
+ done
+}
+
+__tg_refs2 ()
+{
+ local i
+ for i in $(__tg_refs "$1"); do
+ echo "$i:$i"
+ done
+}
+
+__tg_refs_remotes ()
+{
+ local cmd i is_hash=y
+ for i in $(git ls-remote "$1" 2>/dev/null); do
+ case "$is_hash,$i" in
+ n,refs/heads/*)
+ is_hash=y
+ echo "$i:refs/remotes/$1/${i#refs/heads/}"
+ ;;
+ y,*) is_hash=n ;;
+ n,*^{}) is_hash=y ;;
+ n,refs/tags/*) is_hash=y;;
+ n,*) is_hash=y; ;;
+ esac
+ done
+}
+
+__tg_remotes ()
+{
+ local i ngoff IFS=$'\n' d="$(__tgdir)"
+ shopt -q nullglob || ngoff=1
+ shopt -s nullglob
+ for i in "$d/remotes"/*; do
+ echo ${i#$d/remotes/}
+ done
+ [ "$ngoff" ] && shopt -u nullglob
+ for i in $(git --git-dir="$d" config --list); do
+ case "$i" in
+ remote.*.url=*)
+ i="${i#remote.}"
+ echo "${i/.url=*/}"
+ ;;
+ esac
+ done
+}
+
+__tg_complete_revlist ()
+{
+ local pfx cur="${COMP_WORDS[COMP_CWORD]}"
+ case "$cur" in
+ *...*)
+ pfx="${cur%...*}..."
+ cur="${cur#*...}"
+ __tgcomp "$(__tg_refs)" "$pfx" "$cur"
+ ;;
+ *..*)
+ pfx="${cur%..*}.."
+ cur="${cur#*..}"
+ __tgcomp "$(__tg_refs)" "$pfx" "$cur"
+ ;;
+ *)
+ __tgcomp "$(__tg_refs)"
+ ;;
+ esac
+}
+
+__tg_topics ()
+{
+ tg summary | cut -f 2
+}
+
+__tg_commands ()
+{
+ if [ -n "$__tg_all_commandlist" ]; then
+ echo "$__tg_all_commandlist"
+ return
+ fi
+ local i IFS=" "$'\n'
+ for i in $(tg help | sed -n 's/^Usage:.*(\(.*\)).*/\1/p' | tr '|' ' ')
+ do
+ case $i in
+ *--*) : helper pattern;;
+ *) echo $i;;
+ esac
+ done
+}
+__tg_all_commandlist=
+__tg_all_commandlist="$(__tg_commands 2>/dev/null)"
+
+__tg_complete_arg ()
+{
+ if [ $COMP_CWORD -gt 2 ] && [ "${COMP_WORDS[$COMP_CWORD - 1]}" = "$1" ]; then
+ return 0
+ fi
+ return 1
+}
+
+### }}}
+### {{{ Commands
+
+_tg_create ()
+{
+ local cmd="$1"
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ # Name must be the first arg after the create command
+ if [ $((cmd + 1)) = $COMP_CWORD ]; then
+ __tgcomp "$(__tg_topics)"
+ return
+ fi
+
+ __tg_complete_arg "-r" && {
+ __tgcomp "$(__tg_remotes)"
+ return
+ }
+
+ case "$cur" in
+ -*)
+ __tgcomp "
+ -r
+ "
+ ;;
+ *)
+ __tgcomp "$(__tg_refs)"
+ esac
+}
+
+_tg_delete ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ case "$cur" in
+ -*)
+ __tgcomp "
+ -f
+ "
+ ;;
+ *)
+ __tgcomp "$(__tg_topics)"
+ esac
+}
+
+_tg_export ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ __tg_complete_arg "--collapse" && {
+ __tgcomp "$(__tg_heads)"
+ return
+ }
+
+ __tg_complete_arg "--quilt" && {
+ return
+ }
+
+ case "$cur" in
+ *)
+ __tgcomp "
+ --collapse
+ --quilt
+ "
+ esac
+}
+
+_tg_help ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+ case "$cur" in
+ -*)
+ COMPREPLY=()
+ return
+ ;;
+ esac
+ __tgcomp "$(__tg_commands)"
+}
+
+_tg_import ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ __tg_complete_arg "-p" && {
+ COMPREPLY=()
+ return
+ }
+
+ case "$cur" in
+ -*)
+ __tgcomp "
+ -p
+ "
+ ;;
+ *)
+ __tg_complete_revlist
+ esac
+}
+
+_tg_info ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ case "$cur" in
+ *)
+ __tgcomp "$(__tg_topics)"
+ esac
+}
+
+_tg_mail ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ case "$cur" in
+ *)
+ __tgcomp "$(__tg_topics)"
+ esac
+}
+
+_tg_patch ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ case "$cur" in
+ *)
+ __tgcomp "$(__tg_topics)"
+ esac
+}
+
+_tg_remote ()
+{
+ local cur="${COMP_WORDS[COMP_CWORD]}"
+
+ case "$cur" in
+ *)
+ __tgcomp "$(__tg_remotes)"
+ esac
+}
+
+_tg_summary ()
+{
+ COMPREPLY=()
+}
+
+_tg_update ()
+{
+ COMPREPLY=()
+}
+
+### }}}
+### {{{ tg completion
+
+_tg ()
+{
+ local i c=1 command __tg_dir
+
+ while [ $c -lt $COMP_CWORD ]; do
+ i="${COMP_WORDS[c]}"
+ case "$i" in
+ -r)
+ c=$((++c))
+ if [ $c -lt $COMP_CWORD ]; then
+ __tgcomp "$(__tg_remotes)"
+ return
+ fi
+ ;;
+ -h|--help) command="help"; break ;;
+ *) command="$i"; break ;;
+ esac
+ c=$((++c))
+ done
+
+ if [ -z "$command" ]; then
+ case "${COMP_WORDS[COMP_CWORD]}" in
+ -*) __tgcomp "
+ -r
+ -h
+ --help
+ "
+ ;;
+ *) __tgcomp "$(__tg_commands)" ;;
+ esac
+ return
+ fi
+
+ case "$command" in
+ create) _tg_create "$c" ;;
+ delete) _tg_delete ;;
+ export) _tg_export ;;
+ help) _tg_help ;;
+ import) _tg_import ;;
+ info) _tg_info ;;
+ mail) _tg_mail ;;
+ patch) _tg_patch ;;
+ remote) _tg_remote ;;
+ summary) _tg_summary ;;
+ update) _tg_update ;;
+ *) COMPREPLY=() ;;
+ esac
+}
+
+### }}}
+
+ __tgcomp "$(__tg_refs top-bases)"
+complete -o default -o nospace -F _tg tg
+
+# The following are necessary only for Cygwin, and only are needed
+# when the user has tab-completed the executable name and consequently
+# included the '.exe' suffix.
+#
+if [ Cygwin = "$(uname -o 2>/dev/null)" ]; then
+complete -o default -o nospace -F _tg tg.exe
+fi
--
1.6.0.2.471.g47a76.dirty
--
Jonas Fonseca
^ permalink raw reply related [flat|nested] 2+ messages in thread
* [TG PATCH] Complete depend subcommand
2008-09-25 11:06 [TG RFC PATCH] Add bash completion script for TopGit Jonas Fonseca
@ 2008-09-25 13:47 ` Jonas Fonseca
0 siblings, 0 replies; 2+ messages in thread
From: Jonas Fonseca @ 2008-09-25 13:47 UTC (permalink / raw)
To: Petr Baudis, git
Also, removes a debug line and fixes the script header.
Signed-off-by: Jonas Fonseca <fonseca@diku.dk>
---
contrib/tg-completion.bash | 60 ++++++++++++++++++++++++++-----------------
1 files changed, 36 insertions(+), 24 deletions(-)
The completion of the depend command didn't make it into the first
patch because I had a broken topgit usage. Here is a resend, which
also amends the script header.
diff --git a/contrib/tg-completion.bash b/contrib/tg-completion.bash
index 35eabe9..59fbc50 100755
--- a/contrib/tg-completion.bash
+++ b/contrib/tg-completion.bash
@@ -7,32 +7,13 @@
# Conceptually based on gitcompletion (http://gitweb.hawaga.org.uk/).
# Distributed under the GNU General Public License, version 2.0.
#
-# The contained completion routines provide support for completing:
-#
-# *) local and remote branch names
-# *) local and remote tag names
-# *) .git/remotes file names
-# *) git 'subcommands'
-# *) tree paths within 'ref:path/to/file' expressions
-# *) common --long-options
-#
# To use these routines:
#
-# 1) Copy this file to somewhere (e.g. ~/.git-completion.sh).
-# 2) Added the following line to your .bashrc:
-# source ~/.git-completion.sh
-#
-# 3) You may want to make sure the git executable is available
-# in your PATH before this script is sourced, as some caching
-# is performed while the script loads. If git isn't found
-# at source time then all lookups will be done on demand,
-# which may be slightly slower.
+# 1) Copy this file to somewhere (e.g. ~/.tg-completion.sh).
+# 2) Source it from your ~/.bashrc.
#
-# 4) Consider changing your PS1 to also show the current branch:
-# PS1='[\u@\h \W$(__tg_ps1 " (%s)")]\$ '
-#
-# The argument to __tg_ps1 will be displayed only if you
-# are currently in a git repository. The %s token will be
+# Note: Make sure the tg script is in your PATH before you source this
+# script, so it can properly setup cached values.
case "$COMP_WORDBREAKS" in
*:*) : great ;;
@@ -172,6 +153,22 @@ __tg_remotes ()
done
}
+__tg_find_subcommand ()
+{
+ local word subcommand c=1
+
+ while [ $c -lt $COMP_CWORD ]; do
+ word="${COMP_WORDS[c]}"
+ for subcommand in $1; do
+ if [ "$subcommand" = "$word" ]; then
+ echo "$subcommand"
+ return
+ fi
+ done
+ c=$((++c))
+ done
+}
+
__tg_complete_revlist ()
{
local pfx cur="${COMP_WORDS[COMP_CWORD]}"
@@ -268,6 +265,21 @@ _tg_delete ()
esac
}
+_tg_depend ()
+{
+ local subcommands="add"
+ local subcommand="$(__git_find_subcommand "$subcommands")"
+ if [ -z "$subcommand" ]; then
+ __tgcomp "$subcommands"
+ return
+ fi
+
+ case "$subcommand" in
+ add)
+ __tgcomp "$(__tg_refs)"
+ esac
+}
+
_tg_export ()
{
local cur="${COMP_WORDS[COMP_CWORD]}"
@@ -411,6 +423,7 @@ _tg ()
case "$command" in
create) _tg_create "$c" ;;
delete) _tg_delete ;;
+ depend) _tg_depend ;;
export) _tg_export ;;
help) _tg_help ;;
import) _tg_import ;;
@@ -426,7 +439,6 @@ _tg ()
### }}}
- __tgcomp "$(__tg_refs top-bases)"
complete -o default -o nospace -F _tg tg
# The following are necessary only for Cygwin, and only are needed
--
tg: (43a8db8..) jf/completion-fixes (depends on: master)
--
Jonas Fonseca
^ permalink raw reply related [flat|nested] 2+ messages in thread
end of thread, other threads:[~2008-09-25 13:48 UTC | newest]
Thread overview: 2+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2008-09-25 11:06 [TG RFC PATCH] Add bash completion script for TopGit Jonas Fonseca
2008-09-25 13:47 ` [TG PATCH] Complete depend subcommand Jonas Fonseca
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).