2 # bash completion support for core Git.
4 # Copyright (C) 2006 Shawn Pearce
5 # Conceptually based on gitcompletion (http://gitweb.hawaga.org.uk/).
7 # The contained completion routines provide support for completing:
9 # *) local and remote branch names
10 # *) local and remote tag names
11 # *) .git/remotes file names
12 # *) git 'subcommands'
13 # *) tree paths within 'ref:path/to/file' expressions
15 # To use these routines:
17 # 1) Copy this file to somewhere (e.g. ~/.git-completion.sh).
18 # 2) Added the following line to your .bashrc:
19 # source ~/.git-completion.sh
21 # 3) You may want to make sure the git executable is available
22 # in your PATH before this script is sourced, as some caching
23 # is performed while the script loads. If git isn't found
24 # at source time then all lookups will be done on demand,
25 # which may be slightly slower.
27 # 4) Consider changing your PS1 to also show the current branch:
28 # PS1='[\u@\h \W$(__git_ps1 " (%s)")]\$ '
30 # The argument to __git_ps1 will be displayed only if you
31 # are currently in a git repository. The %s token will be
32 # the name of the current branch.
37 echo "${__git_dir:-$(git rev-parse --git-dir 2>/dev/null)}"
42 local b
="$(git symbolic-ref HEAD 2>/dev/null)"
45 printf "$1" "${b##refs/heads/}"
47 printf " (%s)" "${b##refs/heads/}"
54 local cmd i is_hash
=y dir
="${1:-$(__gitdir)}"
55 if [ -d "$dir" ]; then
56 for i
in $
(git
--git-dir="$dir" \
57 for-each-ref
--format='%(refname)' \
59 echo "${i#refs/heads/}"
63 for i
in $
(git-ls-remote
"$dir" 2>/dev
/null
); do
67 n
,refs
/heads
/*) is_hash
=y
; echo "${i#refs/heads/}" ;;
68 n
,*) is_hash
=y
; echo "$i" ;;
75 local cmd i is_hash
=y dir
="${1:-$(__gitdir)}"
76 if [ -d "$dir" ]; then
77 if [ -e "$dir/HEAD" ]; then echo HEAD
; fi
78 for i
in $
(git
--git-dir="$dir" \
79 for-each-ref
--format='%(refname)' \
80 refs
/tags refs
/heads refs
/remotes
); do
82 refs
/tags
/*) echo "${i#refs/tags/}" ;;
83 refs
/heads
/*) echo "${i#refs/heads/}" ;;
84 refs
/remotes
/*) echo "${i#refs/remotes/}" ;;
90 for i
in $
(git-ls-remote
"$dir" 2>/dev
/null
); do
94 n
,refs
/tags
/*) is_hash
=y
; echo "${i#refs/tags/}" ;;
95 n
,refs
/heads
/*) is_hash
=y
; echo "${i#refs/heads/}" ;;
96 n
,refs
/remotes
/*) is_hash
=y
; echo "${i#refs/remotes/}" ;;
97 n
,*) is_hash
=y
; echo "$i" ;;
104 local cmd i is_hash
=y dir
="${1:-$(__gitdir)}"
105 if [ -d "$dir" ]; then
110 for i
in $
($cmd "$dir" 2>/dev
/null
); do
111 case "$is_hash,$i" in
114 n
,refs
/tags
/*) is_hash
=y
; echo "${i#refs/tags/}:${i#refs/tags/}" ;;
115 n
,refs
/heads
/*) is_hash
=y
; echo "${i#refs/heads/}:${i#refs/heads/}" ;;
116 n
,*) is_hash
=y
; echo "$i:$i" ;;
121 __git_refs_remotes
()
123 local cmd i is_hash
=y
124 for i
in $
(git-ls-remote
"$1" 2>/dev
/null
); do
125 case "$is_hash,$i" in
128 echo "$i:refs/remotes/$1/${i#refs/heads/}"
132 n
,refs
/tags
/*) is_hash
=y
;;
140 local i ngoff IFS
=$
'\n' d
="$(__gitdir)"
141 shopt -q nullglob || ngoff
=1
143 for i
in "$d/remotes"/*; do
144 echo ${i#$d/remotes/}
146 [ "$ngoff" ] && shopt -u nullglob
147 for i
in $
(git
--git-dir="$d" repo-config
--list); do
157 __git_merge_strategies
()
159 if [ -n "$__git_merge_strategylist" ]; then
160 echo "$__git_merge_strategylist"
163 sed -n "/^all_strategies='/{
164 s/^all_strategies='//
168 }" "$(git --exec-path)/git-merge"
170 __git_merge_strategylist
=
171 __git_merge_strategylist
="$(__git_merge_strategies 2>/dev/null)"
173 __git_complete_file
()
175 local pfx
ls ref cur
="${COMP_WORDS[COMP_CWORD]}"
191 COMPREPLY
=($
(compgen
-P "$pfx" \
192 -W "$(git --git-dir="$
(__gitdir
)" ls-tree "$ls" \
193 | sed '/^100... blob /s,^.* ,,
202 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
207 __git_complete_revlist
()
209 local pfx cur
="${COMP_WORDS[COMP_CWORD]}"
214 COMPREPLY
=($
(compgen
-P "$pfx" -W "$(__git_refs)" -- "$cur"))
219 COMPREPLY
=($
(compgen
-P "$pfx" -W "$(__git_refs)" -- "$cur"))
222 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
229 if [ -n "$__git_commandlist" ]; then
230 echo "$__git_commandlist"
234 for i
in $
(git
help -a|
egrep '^ ')
237 check-ref-format
) : plumbing
;;
238 commit-tree
) : plumbing
;;
239 convert-objects
) : plumbing
;;
240 cvsserver
) : daemon
;;
242 fetch-pack
) : plumbing
;;
243 hash-object
) : plumbing
;;
244 http-
*) : transport
;;
245 index-pack
) : plumbing
;;
246 local-fetch
) : plumbing
;;
247 mailinfo
) : plumbing
;;
248 mailsplit
) : plumbing
;;
249 merge-
*) : plumbing
;;
252 pack-objects
) : plumbing
;;
253 pack-redundant
) : plumbing
;;
254 pack-refs
) : plumbing
;;
255 parse-remote
) : plumbing
;;
256 patch-id
) : plumbing
;;
257 peek-remote
) : plumbing
;;
258 read-tree
) : plumbing
;;
259 receive-pack
) : plumbing
;;
261 rev-list
) : plumbing
;;
262 rev-parse
) : plumbing
;;
263 runstatus
) : plumbing
;;
264 sh-setup
) : internal
;;
266 send-pack
) : plumbing
;;
267 show-index
) : plumbing
;;
269 stripspace
) : plumbing
;;
270 symbolic-ref
) : plumbing
;;
271 unpack-file
) : plumbing
;;
272 unpack-objects
) : plumbing
;;
273 update-ref
) : plumbing
;;
274 update-server-info
) : daemon
;;
275 upload-archive
) : plumbing
;;
276 upload-pack
) : plumbing
;;
277 write-tree
) : plumbing
;;
283 __git_commandlist
="$(__git_commands 2>/dev/null)"
288 for i
in $
(git
--git-dir="$(__gitdir)" repo-config
--list); do
298 __git_aliased_command
()
300 local word cmdline
=$
(git
--git-dir="$(__gitdir)" \
301 repo-config
--get "alias.$1")
302 for word
in $cmdline; do
303 if [ "${word##-*}" ]; then
310 __git_whitespacelist
="nowarn warn error error-all strip"
314 local cur
="${COMP_WORDS[COMP_CWORD]}"
315 if [ -d .dotest
]; then
316 COMPREPLY
=($
(compgen
-W "
323 COMPREPLY
=($
(compgen
-W "$__git_whitespacelist" \
324 -- "${cur##--whitespace=}"))
328 COMPREPLY
=($
(compgen
-W "
329 --signoff --utf8 --binary --3way --interactive
339 local cur
="${COMP_WORDS[COMP_CWORD]}"
342 COMPREPLY
=($
(compgen
-W "$__git_whitespacelist" \
343 -- "${cur##--whitespace=}"))
347 COMPREPLY
=($
(compgen
-W "
348 --stat --numstat --summary --check --index
349 --cached --index-info --reverse --reject --unidiff-zero
350 --apply --no-add --exclude=
351 --whitespace= --inaccurate-eof --verbose
360 local cur
="${COMP_WORDS[COMP_CWORD]}"
361 COMPREPLY
=($
(compgen
-W "-l -f -d -D $(__git_refs)" -- "$cur"))
366 local cur
="${COMP_WORDS[COMP_CWORD]}"
367 case "${COMP_WORDS[0]},$COMP_CWORD" in
369 COMPREPLY
=($
(compgen
-W "-p -t blob tree commit tag" -- "$cur"))
372 COMPREPLY
=($
(compgen
-W "-p -t blob tree commit tag" -- "$cur"))
382 local cur
="${COMP_WORDS[COMP_CWORD]}"
383 COMPREPLY
=($
(compgen
-W "-l -b $(__git_refs)" -- "$cur"))
388 local cur
="${COMP_WORDS[COMP_CWORD]}"
391 COMPREPLY
=($
(compgen
-W "
396 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
403 local cur
="${COMP_WORDS[COMP_CWORD]}"
406 COMPREPLY
=($
(compgen
-W "
407 --all --author= --signoff --verify --no-verify
408 --edit --amend --include --only
422 local cur
="${COMP_WORDS[COMP_CWORD]}"
423 COMPREPLY
=($
(compgen
-W "-r -p -M $(__git_refs)" -- "$cur"))
428 local cur
="${COMP_WORDS[COMP_CWORD]}"
430 case "${COMP_WORDS[0]},$COMP_CWORD" in
432 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
435 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
441 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
445 case "${COMP_WORDS[0]}" in
446 git-fetch
) remote
="${COMP_WORDS[1]}" ;;
447 git
) remote
="${COMP_WORDS[2]}" ;;
449 COMPREPLY
=($
(compgen
-W "$(__git_refs2 "$remote")" -- "$cur"))
458 local cur
="${COMP_WORDS[COMP_CWORD]}"
461 COMPREPLY
=($
(compgen
-W "
462 --stdout --attach --thread
464 --numbered --start-number
468 --full-index --binary
473 __git_complete_revlist
478 local cur
="${COMP_WORDS[COMP_CWORD]}"
479 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
489 local cur
="${COMP_WORDS[COMP_CWORD]}"
492 COMPREPLY
=($
(compgen
-W "
493 oneline short medium full fuller email raw
494 " -- "${cur##--pretty=}"))
498 COMPREPLY
=($
(compgen
-W "
499 --max-count= --max-age= --since= --after=
500 --min-age= --before= --until=
501 --root --not --topo-order --date-order
503 --abbrev-commit --abbrev=
505 --author= --committer= --grep=
507 --pretty= --name-status --name-only
512 __git_complete_revlist
517 local cur
="${COMP_WORDS[COMP_CWORD]}"
518 case "${COMP_WORDS[COMP_CWORD-1]}" in
520 COMPREPLY
=($
(compgen
-W "$(__git_merge_strategies)" -- "$cur"))
525 COMPREPLY
=($
(compgen
-W "$(__git_merge_strategies)" \
526 -- "${cur##--strategy=}"))
530 COMPREPLY
=($
(compgen
-W "
531 --no-commit --no-summary --squash --strategy
535 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
540 local cur
="${COMP_WORDS[COMP_CWORD]}"
541 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
546 local cur
="${COMP_WORDS[COMP_CWORD]}"
547 COMPREPLY
=($
(compgen
-W "--tags --all --stdin" -- "$cur"))
552 local cur
="${COMP_WORDS[COMP_CWORD]}"
554 case "${COMP_WORDS[0]},$COMP_CWORD" in
556 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
559 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
563 case "${COMP_WORDS[0]}" in
564 git-pull
) remote
="${COMP_WORDS[1]}" ;;
565 git
) remote
="${COMP_WORDS[2]}" ;;
567 COMPREPLY
=($
(compgen
-W "$(__git_refs "$remote")" -- "$cur"))
574 local cur
="${COMP_WORDS[COMP_CWORD]}"
576 case "${COMP_WORDS[0]},$COMP_CWORD" in
578 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
581 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
587 case "${COMP_WORDS[0]}" in
588 git-push
) remote
="${COMP_WORDS[1]}" ;;
589 git
) remote
="${COMP_WORDS[2]}" ;;
592 COMPREPLY
=($
(compgen
-W "$(__git_refs "$remote")" -- "$cur"))
595 COMPREPLY
=($
(compgen
-W "$(__git_refs2)" -- "$cur"))
604 local cur
="${COMP_WORDS[COMP_CWORD]}"
605 if [ -d .dotest
]; then
606 COMPREPLY
=($
(compgen
-W "
607 --continue --skip --abort
611 case "${COMP_WORDS[COMP_CWORD-1]}" in
613 COMPREPLY
=($
(compgen
-W "$(__git_merge_strategies)" -- "$cur"))
618 COMPREPLY
=($
(compgen
-W "$(__git_merge_strategies)" \
619 -- "${cur##--strategy=}"))
623 COMPREPLY
=($
(compgen
-W "
624 --onto --merge --strategy
628 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
633 local cur
="${COMP_WORDS[COMP_CWORD]}"
634 local prv
="${COMP_WORDS[COMP_CWORD-1]}"
637 COMPREPLY
=($
(compgen
-W "$(__git_remotes)" -- "$cur"))
641 COMPREPLY
=($
(compgen
-W "$(__git_refs)" -- "$cur"))
645 local remote
="${prv#remote.}"
646 remote
="${remote%.fetch}"
647 COMPREPLY
=($
(compgen
-W "$(__git_refs_remotes "$remote")" \
652 local remote
="${prv#remote.}"
653 remote
="${remote%.push}"
654 COMPREPLY
=($
(compgen
-W "$(git --git-dir="$
(__gitdir
)" \
655 for-each-ref --format='%(refname):%(refname)' \
656 refs/heads)" -- "$cur"))
666 COMPREPLY
=($
(compgen
-W "
667 --global --list --replace-all
668 --get --get-all --get-regexp
674 local pfx
="${cur%.*}."
676 COMPREPLY
=($
(compgen
-P "$pfx" -W "remote merge" -- "$cur"))
680 local pfx
="${cur%.*}."
682 COMPREPLY
=($
(compgen
-P "$pfx" -S . \
683 -W "$(__git_heads)" -- "$cur"))
687 local pfx
="${cur%.*}."
689 COMPREPLY
=($
(compgen
-P "$pfx" -W "url fetch push" -- "$cur"))
693 local pfx
="${cur%.*}."
695 COMPREPLY
=($
(compgen
-P "$pfx" -S . \
696 -W "$(__git_remotes)" -- "$cur"))
700 COMPREPLY
=($
(compgen
-W "
705 core.preferSymlinkRefs
706 core.logAllRefUpdates
707 core.repositoryFormatVersion
708 core.sharedRepository
709 core.warnAmbiguousRefs
728 http.lowSpeedLimit http.lowSpeedTime
731 repack.useDeltaBaseOffset
732 pull.octopus pull.twohead
735 receive.denyNonFastForwards
746 local cur
="${COMP_WORDS[COMP_CWORD]}"
747 local opt
="--mixed --hard --soft"
748 COMPREPLY
=($
(compgen
-W "$opt $(__git_refs)" -- "$cur"))
753 local i c
=1 command __git_dir
755 while [ $c -lt $COMP_CWORD ]; do
758 --git-dir=*) __git_dir
="${i#--git-dir=}" ;;
759 --bare) __git_dir
="." ;;
760 --version|
--help|
-p|
--paginate) ;;
761 *) command="$i"; break ;;
766 if [ $c -eq $COMP_CWORD -a -z "$command" ]; then
767 COMPREPLY
=($
(compgen
-W "
768 --git-dir= --version --exec-path
771 " -- "${COMP_WORDS[COMP_CWORD]}"))
775 local expansion
=$
(__git_aliased_command
"$command")
776 [ "$expansion" ] && command="$expansion"
781 branch
) _git_branch
;;
782 cat-file
) _git_cat_file
;;
783 checkout
) _git_checkout
;;
784 cherry-pick
) _git_cherry_pick
;;
785 commit
) _git_commit
;;
787 diff-tree
) _git_diff_tree
;;
789 format-patch
) _git_format_patch
;;
791 ls-remote
) _git_ls_remote
;;
792 ls-tree
) _git_ls_tree
;;
794 merge-base
) _git_merge_base
;;
795 name-rev
) _git_name_rev
;;
798 rebase
) _git_rebase
;;
799 repo-config
) _git_repo_config
;;
802 show-branch
) _git_log
;;
803 whatchanged
) _git_log
;;
810 local cur
="${COMP_WORDS[COMP_CWORD]}"
811 COMPREPLY
=($
(compgen
-W "--all $(__git_refs)" -- "$cur"))
814 complete
-o default
-o nospace
-F _git git
815 complete
-o default
-F _gitk gitk
816 complete
-o default
-F _git_am git-am
817 complete
-o default
-F _git_apply git-apply
818 complete
-o default
-F _git_branch git-branch
819 complete
-o default
-o nospace
-F _git_cat_file git-cat-file
820 complete
-o default
-F _git_checkout git-checkout
821 complete
-o default
-F _git_cherry_pick git-cherry-pick
822 complete
-o default
-F _git_commit git-commit
823 complete
-o default
-o nospace
-F _git_diff git-diff
824 complete
-o default
-F _git_diff_tree git-diff-tree
825 complete
-o default
-o nospace
-F _git_fetch git-fetch
826 complete
-o default
-o nospace
-F _git_format_patch git-format-patch
827 complete
-o default
-o nospace
-F _git_log git-log
828 complete
-o default
-F _git_ls_remote git-ls-remote
829 complete
-o default
-o nospace
-F _git_ls_tree git-ls-tree
830 complete
-o default
-F _git_merge git-merge
831 complete
-o default
-F _git_merge_base git-merge-base
832 complete
-o default
-F _git_name_rev git-name-rev
833 complete
-o default
-o nospace
-F _git_pull git-pull
834 complete
-o default
-o nospace
-F _git_push git-push
835 complete
-o default
-F _git_rebase git-rebase
836 complete
-o default
-F _git_repo_config git-repo-config
837 complete
-o default
-F _git_reset git-reset
838 complete
-o default
-F _git_log git-show
839 complete
-o default
-o nospace
-F _git_log git-show-branch
840 complete
-o default
-o nospace
-F _git_log git-whatchanged
842 # The following are necessary only for Cygwin, and only are needed
843 # when the user has tab-completed the executable name and consequently
844 # included the '.exe' suffix.
846 if [ Cygwin
= "$(uname -o 2>/dev/null)" ]; then
847 complete
-o default
-F _git_apply git-apply.exe
848 complete
-o default
-o nospace
-F _git git.exe
849 complete
-o default
-F _git_branch git-branch.exe
850 complete
-o default
-o nospace
-F _git_cat_file git-cat-file.exe
851 complete
-o default
-o nospace
-F _git_diff git-diff.exe
852 complete
-o default
-o nospace
-F _git_diff_tree git-diff-tree.exe
853 complete
-o default
-o nospace
-F _git_format_patch git-format-patch.exe
854 complete
-o default
-o nospace
-F _git_log git-log.exe
855 complete
-o default
-o nospace
-F _git_ls_tree git-ls-tree.exe
856 complete
-o default
-F _git_merge_base git-merge-base.exe
857 complete
-o default
-F _git_name_rev git-name-rev.exe
858 complete
-o default
-o nospace
-F _git_push git-push.exe
859 complete
-o default
-F _git_repo_config git-repo-config
860 complete
-o default
-o nospace
-F _git_log git-show.exe
861 complete
-o default
-o nospace
-F _git_log git-show-branch.exe
862 complete
-o default
-o nospace
-F _git_log git-whatchanged.exe