Commit | Line | Data |
---|---|---|
d195d49e JF |
1 | ## |
2 | # bash completion support for tig | |
3 | # | |
4 | # Copyright (C) 2007 Jonas fonseca | |
5 | # Copyright (C) 2006,2007 Shawn Pearce | |
6 | # | |
7 | # Based git's git-completion.sh: http://repo.or.cz/w/git/fastimport.git | |
8 | # | |
9 | # The contained completion routines provide support for completing: | |
10 | # | |
11 | # *) local and remote branch names | |
12 | # *) local and remote tag names | |
13 | # *) tig 'subcommands' | |
14 | # *) tree paths within 'ref:path/to/file' expressions | |
15 | # | |
16 | # To use these routines: | |
17 | # | |
18 | # 1) Copy this file to somewhere (e.g. ~/.tig-completion.sh). | |
19 | # 2) Added the following line to your .bashrc: | |
20 | # source ~/.tig-completion.sh | |
21 | # | |
22 | # 3) You may want to make sure the git executable is available | |
23 | # in your PATH before this script is sourced, as some caching | |
24 | # is performed while the script loads. If git isn't found | |
25 | # at source time then all lookups will be done on demand, | |
26 | # which may be slightly slower. | |
27 | # | |
28 | ||
29 | __tigdir () | |
30 | { | |
31 | if [ -z "$1" ]; then | |
32 | if [ -n "$__git_dir" ]; then | |
33 | echo "$__git_dir" | |
34 | elif [ -d .git ]; then | |
35 | echo .git | |
36 | else | |
37 | git rev-parse --git-dir 2>/dev/null | |
38 | fi | |
39 | elif [ -d "$1/.git" ]; then | |
40 | echo "$1/.git" | |
41 | else | |
42 | echo "$1" | |
43 | fi | |
44 | } | |
45 | ||
46 | tigcomp () | |
47 | { | |
48 | local all c s=$'\n' IFS=' '$'\t'$'\n' | |
49 | local cur="${COMP_WORDS[COMP_CWORD]}" | |
50 | if [ $# -gt 2 ]; then | |
51 | cur="$3" | |
52 | fi | |
53 | for c in $1; do | |
54 | case "$c$4" in | |
55 | --*=*) all="$all$c$4$s" ;; | |
56 | *.) all="$all$c$4$s" ;; | |
57 | *) all="$all$c$4 $s" ;; | |
58 | esac | |
59 | done | |
60 | IFS=$s | |
61 | COMPREPLY=($(compgen -P "$2" -W "$all" -- "$cur")) | |
62 | return | |
63 | } | |
64 | ||
65 | __tig_refs () | |
66 | { | |
67 | local cmd i is_hash=y dir="$(__tigdir "$1")" | |
68 | if [ -d "$dir" ]; then | |
69 | if [ -e "$dir/HEAD" ]; then echo HEAD; fi | |
70 | for i in $(git --git-dir="$dir" \ | |
71 | for-each-ref --format='%(refname)' \ | |
72 | refs/tags refs/heads refs/remotes); do | |
73 | case "$i" in | |
74 | refs/tags/*) echo "${i#refs/tags/}" ;; | |
75 | refs/heads/*) echo "${i#refs/heads/}" ;; | |
76 | refs/remotes/*) echo "${i#refs/remotes/}" ;; | |
77 | *) echo "$i" ;; | |
78 | esac | |
79 | done | |
80 | return | |
81 | fi | |
82 | for i in $(git-ls-remote "$dir" 2>/dev/null); do | |
83 | case "$is_hash,$i" in | |
84 | y,*) is_hash=n ;; | |
85 | n,*^{}) is_hash=y ;; | |
86 | n,refs/tags/*) is_hash=y; echo "${i#refs/tags/}" ;; | |
87 | n,refs/heads/*) is_hash=y; echo "${i#refs/heads/}" ;; | |
88 | n,refs/remotes/*) is_hash=y; echo "${i#refs/remotes/}" ;; | |
89 | n,*) is_hash=y; echo "$i" ;; | |
90 | esac | |
91 | done | |
92 | } | |
93 | ||
94 | __tig_complete_file () | |
95 | { | |
96 | local pfx ls ref cur="${COMP_WORDS[COMP_CWORD]}" | |
97 | case "$cur" in | |
98 | ?*:*) | |
99 | ref="${cur%%:*}" | |
100 | cur="${cur#*:}" | |
101 | case "$cur" in | |
102 | ?*/*) | |
103 | pfx="${cur%/*}" | |
104 | cur="${cur##*/}" | |
105 | ls="$ref:$pfx" | |
106 | pfx="$pfx/" | |
107 | ;; | |
108 | *) | |
109 | ls="$ref" | |
110 | ;; | |
111 | esac | |
112 | COMPREPLY=($(compgen -P "$pfx" \ | |
113 | -W "$(git --git-dir="$(__tigdir)" ls-tree "$ls" \ | |
114 | | sed '/^100... blob /s,^.* ,, | |
115 | /^040000 tree /{ | |
116 | s,^.* ,, | |
117 | s,$,/, | |
118 | } | |
119 | s/^.* //')" \ | |
120 | -- "$cur")) | |
121 | ;; | |
122 | *) | |
123 | tigcomp "$(__tig_refs)" | |
124 | ;; | |
125 | esac | |
126 | } | |
127 | ||
128 | __tig_complete_revlist () | |
129 | { | |
130 | local pfx cur="${COMP_WORDS[COMP_CWORD]}" | |
131 | case "$cur" in | |
132 | *...*) | |
133 | pfx="${cur%...*}..." | |
134 | cur="${cur#*...}" | |
135 | tigcomp "$(__tig_refs)" "$pfx" "$cur" | |
136 | ;; | |
137 | *..*) | |
138 | pfx="${cur%..*}.." | |
139 | cur="${cur#*..}" | |
140 | tigcomp "$(__tig_refs)" "$pfx" "$cur" | |
141 | ;; | |
142 | *.) | |
143 | tigcomp "$cur." | |
144 | ;; | |
145 | *) | |
146 | tigcomp "$(__tig_refs)" | |
147 | ;; | |
148 | esac | |
149 | } | |
150 | ||
151 | _tig_diff () | |
152 | { | |
153 | __tig_complete_file | |
154 | } | |
155 | ||
156 | _tig_log () | |
157 | { | |
158 | local cur="${COMP_WORDS[COMP_CWORD]}" | |
159 | case "$cur" in | |
160 | --pretty=*) | |
161 | tigcomp " | |
162 | oneline short medium full fuller email raw | |
163 | " "" "${cur##--pretty=}" | |
164 | return | |
165 | ;; | |
166 | --*) | |
167 | tigcomp " | |
168 | --max-count= --max-age= --since= --after= | |
169 | --min-age= --before= --until= | |
170 | --root --not --topo-order --date-order | |
171 | --no-merges | |
172 | --abbrev-commit --abbrev= | |
173 | --relative-date | |
174 | --author= --committer= --grep= | |
175 | --all-match | |
176 | --pretty= --name-status --name-only | |
177 | --not --all | |
178 | " | |
179 | return | |
180 | ;; | |
181 | esac | |
182 | __tig_complete_revlist | |
183 | } | |
184 | ||
185 | _tig_show () | |
186 | { | |
187 | local cur="${COMP_WORDS[COMP_CWORD]}" | |
188 | case "$cur" in | |
189 | --pretty=*) | |
190 | tigcomp " | |
191 | oneline short medium full fuller email raw | |
192 | " "" "${cur##--pretty=}" | |
193 | return | |
194 | ;; | |
195 | --*) | |
196 | tigcomp "--pretty=" | |
197 | return | |
198 | ;; | |
199 | esac | |
200 | __tig_complete_file | |
201 | } | |
202 | ||
203 | _tig () | |
204 | { | |
205 | local i c=1 command __tig_dir | |
206 | ||
207 | while [ $c -lt $COMP_CWORD ]; do | |
208 | i="${COMP_WORDS[c]}" | |
209 | case "$i" in | |
210 | --) command="log"; break;; | |
211 | -*) ;; | |
212 | *) command="$i"; break ;; | |
213 | esac | |
214 | c=$((++c)) | |
215 | done | |
216 | ||
217 | if [ $c -eq $COMP_CWORD -a -z "$command" ]; then | |
218 | case "${COMP_WORDS[COMP_CWORD]}" in | |
219 | --*=*) COMPREPLY=() ;; | |
72f09621 | 220 | -*) tigcomp " |
d195d49e JF |
221 | --line-number= --tab-size= --version --help |
222 | -b -d -h -l -S -v | |
223 | " ;; | |
72f09621 | 224 | *) tigcomp "log diff show $(__tig_refs)" ;; |
d195d49e JF |
225 | esac |
226 | return | |
227 | fi | |
228 | ||
229 | case "$command" in | |
230 | diff) _tig_diff ;; | |
231 | show) _tig_show ;; | |
232 | log) _tig_log ;; | |
233 | *) tigcomp " | |
234 | $(__tig_complete_file) | |
235 | $(__tig_refs) | |
236 | " ;; | |
237 | esac | |
238 | } | |
239 | ||
240 | complete -o default -o nospace -F _tig tig | |
241 | ||
242 | # The following are necessary only for Cygwin, and only are needed | |
243 | # when the user has tab-completed the executable name and consequently | |
244 | # included the '.exe' suffix. | |
245 | if [ Cygwin = "$(uname -o 2>/dev/null)" ]; then | |
246 | complete -o default -o nospace -F _tig tig.exe | |
247 | fi |