git.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 00/51] completion: revamp
@ 2022-08-30  9:30 Felipe Contreras
  2022-08-30  9:30 ` [PATCH 01/51] test: completion add test for __git_cmd_idx Felipe Contreras
                   ` (50 more replies)
  0 siblings, 51 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

This patch series revamps the completion code to git-completion 1.4.

I used to send this series minimizing the delta to git upstream in order
to maximize the chances of it being merged, but it has not received any
feedback since the first time it was sent in 2020 [1], so it is safe to
say upstream has zero interest in getting this merged. It makes no sense
for me to do extra work to maximize the chances of something that will
never happen.

Therefore this series starts with the most intrusive change:
zsh completion tests.

For several years git-completion has been running zsh completion tests
to make sure everything works correctly, not only for bash, but also for
zsh.

The zsh code delta between upstream and git-completion results in 14
tests now passing. The new patch series makes that clear now.

Here's a summary of the differences between upstream and git-completion:

 * Fixed alias regression
 * Make tests work when user has configured GIT_PS1_* variables
 * Enable colors in bash without prompt command
 * Fix suboptions for zsh
 * Fix COMP_WORDBREAKS handling
 * Fix main option handling for zsh
 * Fix -C handling for zsh
 * Fix -c handling for zsh
 * Fix generic completions for zsh
 * Fix configurations with value for zsh (e1e00089da)
 * Fix option relationships for zsh
 * Add improved removable suffix for zsh
 * Plenty of reorganizations and cleanups

For more information check [2].

Cheers.

[1] https://lore.kernel.org/git/20201110212136.870769-1-felipe.contreras@gmail.com/
[2] https://github.com/felipec/git-completion

Felipe Contreras (50):
  test: completion add test for __git_cmd_idx
  test: add zsh completion tests
  completion: fix __git_cmd_idx regression for zsh
  completion: bash: trivial cleanup
  completion: zsh: add higher-priority location
  zsh: simplify realpath dirname idiom
  test: reset environment variables
  completion: prompt: use generic colors
  completion: fix for suboptions with value
  completion: zsh: trivial improvement
  completion: bash: do not modify COMP_WORDBREAKS
  test: completion: fix currently typed words
  test: completion: switch __gitcomp_nl prefix test
  test: completion: add run_func() helper
  completion: bash: remove non-append functionality
  completion: bash: get rid of _append() functions
  completion: bash: get rid of any non-append code
  completion: zsh: fix options with arguments
  completion: zsh: expand --git-dir file argument
  completion: zsh: add support for general -C opts
  completion: zsh: fix for undefined completions
  completion: zsh: add support for general -c opts
  completion: zsh: fix extra space on foo=
  completion: zsh: add excluded options
  completion: zsh: always set compset
  completion: factor out check in __gitcomp
  completion: simplify equal suffix check
  completion: refactor __gitcomp
  completion: simplify __gitcomp
  completion: bash: change suffix check in __gitcomp
  completion: improve __gitcomp suffix code
  test: completion: add missing test
  completion: bash: simplify config_variable_name
  completion: bash: improve __gitcomp description
  completion: add __gitcomp_opts
  completion: bash: cleanup __gitcomp* invocations
  completion: bash: shuffle __gitcomp functions
  completion: zsh: simplify __gitcomp_direct
  completion: zsh: shuffle __gitcomp* functions
  completion: zsh: fix direct quoting
  completion: zsh: add elements individually in __gitcomp_opts
  completion: zsh: add __gitcompadd helper
  completion: zsh: add correct removable suffix
  completion: bash: simplify _get_comp_words_by_ref()
  completion: bash: refactor _get_comp_words_by_ref()
  completion: bash: cleanup _get_comp_words_by_ref()
  completion: bash: trivial cleanup
  completion: bash: rename _get_comp_words_by_ref()
  zsh: remove version
  completion: bash: trivial grammar fix

Michael Bianco (1):
  zsh: resolve symlink of script

 contrib/completion/git-completion.bash |  637 ++++++-------
 contrib/completion/git-completion.zsh  |  146 ++-
 contrib/completion/git-prompt.sh       |   19 +-
 t/t9902-completion.sh                  |  159 ++--
 t/t9903-bash-prompt.sh                 |   16 +-
 t/t9904-zsh-completion.sh              | 1137 ++++++++++++++++++++++++
 t/t9904/.gitignore                     |    1 +
 t/t9904/.zshrc                         |   50 ++
 t/t9904/_git                           |    1 +
 t/t9904/completion                     |   11 +
 10 files changed, 1649 insertions(+), 528 deletions(-)
 create mode 100755 t/t9904-zsh-completion.sh
 create mode 100644 t/t9904/.gitignore
 create mode 100644 t/t9904/.zshrc
 create mode 120000 t/t9904/_git
 create mode 100755 t/t9904/completion

-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply	[flat|nested] 52+ messages in thread

* [PATCH 01/51] test: completion add test for __git_cmd_idx
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 02/51] test: add zsh completion tests Felipe Contreras
                   ` (49 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

When __git_func_wrap was fixed to set correctly __git_cmd_idx in
cea232194d (completion: bash: fix late declaration of __git_cmd_idx,
2021-06-18) no test was added, therefore we could hit the same bug in
the future.

To ensure that doesn't happen add a test which adds an alias for 'git
add' with __git_complete, and then pretend the user typed this alias.

To make sure __git_cmd_idx is correct we add the --update option to
ensure the result of __git_find_on_cmdline (which uses __git_cmd_idx) is
correct. When __git_cmd_idx isn't correct __git_find_on_cmdline fails,
and therefore the --update option isn't interpreted correctly.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9902-completion.sh | 9 +++++++++
 1 file changed, 9 insertions(+)

diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index 43de868b80..8cc30448c7 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -2659,4 +2659,13 @@ test_expect_success '__git_complete' '
 	test_must_fail __git_complete ga missing
 '
 
+test_expect_success '__git_complete has correct __git_cmd_idx' '
+	__git_complete ga _git_add &&
+	echo modified > file1 &&
+	touch file3 &&
+	_words=(ga --update f) _cword=2 &&
+	__git_wrap_git_add &&
+	test "${COMPREPLY[*]}" = "file1"
+'
+
 test_done
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 02/51] test: add zsh completion tests
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
  2022-08-30  9:30 ` [PATCH 01/51] test: completion add test for __git_cmd_idx Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 03/51] completion: fix __git_cmd_idx regression for zsh Felipe Contreras
                   ` (48 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

zsh's completion system is very advanced, but that comes with a
disadvantage: there is no easy way to dump the completions. The simplest
way of doing that is printing them to stdout in a certain format, and
then use the zpty module to parse that format and actually print them.

There is no easier way.

We also have to simulate `compadd` in order to output the list of
completions in a way that is similar to the bash completion tests.

The resulting test scripts is very close to the bash completion test
script, except some tests don't make sense, and others require minor
modifications.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9904-zsh-completion.sh | 1124 +++++++++++++++++++++++++++++++++++++
 t/t9904/.gitignore        |    1 +
 t/t9904/.zshrc            |   50 ++
 t/t9904/_git              |    1 +
 t/t9904/completion        |   11 +
 5 files changed, 1187 insertions(+)
 create mode 100755 t/t9904-zsh-completion.sh
 create mode 100644 t/t9904/.gitignore
 create mode 100644 t/t9904/.zshrc
 create mode 120000 t/t9904/_git
 create mode 100755 t/t9904/completion

diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
new file mode 100755
index 0000000000..5179b2dc76
--- /dev/null
+++ b/t/t9904-zsh-completion.sh
@@ -0,0 +1,1124 @@
+#!/bin/bash
+#
+# Copyright (c) 2012-2022 Felipe Contreras
+#
+
+test_description='test zsh completion'
+
+. ./lib-bash.sh
+
+if ! command -v zsh > /dev/null 2>&1; then
+	skip_all='skipping completion zsh tests: zsh not available'
+	test_done
+fi
+
+export GIT_BUILD_DIR
+
+run_completion ()
+{
+	"$TEST_DIRECTORY/t9904/completion" "$1" > out
+	[[ -s out ]] || { echo > out ; }
+}
+
+# Test high-level completion
+# Arguments are:
+# 1: typed text so far (cur)
+# 2: expected completion
+test_completion ()
+{
+	if test $# -gt 1
+	then
+		printf '%s\n' "$2" >expected
+	else
+		sed -e 's/Z$//' |sort >expected
+	fi &&
+	run_completion "$1" &&
+	sort -u out >out_sorted &&
+	test_cmp expected out_sorted
+}
+
+# Test __gitcomp.
+# The first argument is the typed text so far (cur); the rest are
+# passed to __gitcomp.  Expected output comes is read from the
+# standard input, like test_completion().
+test_gitcomp ()
+{
+	sed -e 's/Z$//' >expected &&
+	local cur="$1" &&
+	shift &&
+	run_completion "git func __gitcomp $(printf "%q " "$@") $cur" &&
+	test_cmp expected out
+}
+
+# Test __gitcomp_nl
+# Arguments are:
+# 1: current word (cur)
+# -: the rest are passed to __gitcomp_nl
+test_gitcomp_nl ()
+{
+	sed -e "s/Z$//" >expected &&
+	local cur="$1" &&
+	shift &&
+	run_completion "git func __gitcomp_nl $(printf "%q " "$@") $cur" &&
+	test_cmp expected out
+}
+
+actual="$TRASH_DIRECTORY/actual"
+
+if test_have_prereq MINGW
+then
+	ROOT="$(pwd -W)"
+else
+	ROOT="$(pwd)"
+fi
+
+test_expect_success 'setup for __git_find_repo_path/__gitdir tests' '
+	mkdir -p subdir/subsubdir &&
+	mkdir -p non-repo &&
+	git init -b main otherrepo
+'
+
+test_expect_success '__gitcomp - trailing space - options' '
+	test_gitcomp "--re" "--dry-run --reuse-message= --reedit-message=
+		--reset-author" <<-EOF
+	--reuse-message=Z
+	--reedit-message=Z
+	--reset-author Z
+	EOF
+'
+
+test_expect_success '__gitcomp - trailing space - config keys' '
+	test_gitcomp "br" "branch. branch.autosetupmerge
+		branch.autosetuprebase browser." <<-\EOF
+	branch.Z
+	branch.autosetupmerge Z
+	branch.autosetuprebase Z
+	browser.Z
+	EOF
+'
+
+test_expect_success '__gitcomp - option parameter' '
+	test_gitcomp "--strategy=re" "octopus ours recursive resolve subtree" \
+		"" "re" <<-\EOF
+	recursive Z
+	resolve Z
+	EOF
+'
+
+test_expect_failure '__gitcomp - prefix' '
+	test_gitcomp "branch.me" "remote merge mergeoptions rebase" \
+		"branch.maint." "me" <<-\EOF
+	branch.maint.merge Z
+	branch.maint.mergeoptions Z
+	EOF
+'
+
+test_expect_failure '__gitcomp - suffix' '
+	test_gitcomp "branch.me" "master maint next seen" "branch." \
+		"ma" "." <<-\EOF
+	branch.master.Z
+	branch.maint.Z
+	EOF
+'
+
+test_expect_success '__gitcomp - ignore optional negative options' '
+	test_gitcomp "--" "--abc --def --no-one -- --no-two" <<-\EOF
+	--abc Z
+	--def Z
+	--no-one Z
+	--no-... Z
+	EOF
+'
+
+test_expect_success '__gitcomp - ignore/narrow optional negative options' '
+	test_gitcomp "--a" "--abc --abcdef --no-one -- --no-two" <<-\EOF
+	--abc Z
+	--abcdef Z
+	EOF
+'
+
+test_expect_success '__gitcomp - ignore/narrow optional negative options' '
+	test_gitcomp "--n" "--abc --def --no-one -- --no-two" <<-\EOF
+	--no-one Z
+	--no-... Z
+	EOF
+'
+
+test_expect_success '__gitcomp - expand all negative options' '
+	test_gitcomp "--no-" "--abc --def --no-one -- --no-two" <<-\EOF
+	--no-one Z
+	--no-two Z
+	EOF
+'
+
+test_expect_success '__gitcomp - expand/narrow all negative options' '
+	test_gitcomp "--no-o" "--abc --def --no-one -- --no-two" <<-\EOF
+	--no-one Z
+	EOF
+'
+
+test_expect_failure '__gitcomp - equal skip' '
+	test_gitcomp "--option=" "--option=" <<-\EOF &&
+
+	EOF
+	test_gitcomp "option=" "option=" <<-\EOF
+
+	EOF
+'
+
+read -r -d "" refs <<-\EOF
+main
+maint
+next
+seen
+EOF
+
+test_expect_success '__gitcomp_nl - trailing space' '
+	test_gitcomp_nl "m" "$refs" <<-EOF
+	main Z
+	maint Z
+	EOF
+'
+
+test_expect_failure '__gitcomp_nl - prefix' '
+	test_gitcomp_nl "--fixup=m" "$refs" "--fixup=" "m" <<-EOF
+	--fixup=main Z
+	--fixup=maint Z
+	EOF
+'
+
+test_expect_success '__gitcomp_nl - suffix' '
+	test_gitcomp_nl "branch.ma" "$refs" "branch." "ma" "." <<-\EOF
+	branch.main.Z
+	branch.maint.Z
+	EOF
+'
+
+test_expect_success '__gitcomp_nl - no suffix' '
+	test_gitcomp_nl "ma" "$refs" "" "ma" "" <<-\EOF
+	mainZ
+	maintZ
+	EOF
+'
+
+test_expect_success 'setup for ref completion' '
+	git commit --allow-empty -m initial &&
+	git branch -M main &&
+	git branch matching-branch &&
+	git tag matching-tag &&
+	(
+		cd otherrepo &&
+		git commit --allow-empty -m initial &&
+		git branch -m main main-in-other &&
+		git branch branch-in-other &&
+		git tag tag-in-other
+	) &&
+	git remote add other "$ROOT/otherrepo/.git" &&
+	git fetch --no-tags other &&
+	rm -f .git/FETCH_HEAD &&
+	git init thirdrepo
+'
+
+test_expect_success 'git switch - with no options, complete local branches and unique remote branch names for DWIM logic' '
+	test_completion "git switch " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - completes refs and unique remote branches for DWIM' '
+	test_completion "git checkout " <<-\EOF
+	HEAD Z
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with --no-guess, complete only local branches' '
+	test_completion "git switch --no-guess " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - with GIT_COMPLETION_CHECKOUT_NO_GUESS=1, complete only local branches' '
+	GIT_COMPLETION_CHECKOUT_NO_GUESS=1 test_completion "git switch " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - --guess overrides GIT_COMPLETION_CHECKOUT_NO_GUESS=1, complete local branches and unique remote names for DWIM logic' '
+	GIT_COMPLETION_CHECKOUT_NO_GUESS=1 test_completion "git switch --guess " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - a later --guess overrides previous --no-guess, complete local and remote unique branches for DWIM' '
+	test_completion "git switch --no-guess --guess " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - a later --no-guess overrides previous --guess, complete only local branches' '
+	test_completion "git switch --guess --no-guess " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - with GIT_COMPLETION_NO_GUESS=1 only completes refs' '
+	GIT_COMPLETION_CHECKOUT_NO_GUESS=1 test_completion "git checkout " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - --guess overrides GIT_COMPLETION_NO_GUESS=1, complete refs and unique remote branches for DWIM' '
+	GIT_COMPLETION_CHECKOUT_NO_GUESS=1 test_completion "git checkout --guess " <<-\EOF
+	HEAD Z
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with --no-guess, only completes refs' '
+	test_completion "git checkout --no-guess " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - a later --guess overrides previous --no-guess, complete refs and unique remote branches for DWIM' '
+	test_completion "git checkout --no-guess --guess " <<-\EOF
+	HEAD Z
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - a later --no-guess overrides previous --guess, complete only refs' '
+	test_completion "git checkout --guess --no-guess " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with checkout.guess = false, only completes refs' '
+	test_config checkout.guess false &&
+	test_completion "git checkout " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with checkout.guess = true, completes refs and unique remote branches for DWIM' '
+	test_config checkout.guess true &&
+	test_completion "git checkout " <<-\EOF
+	HEAD Z
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - a later --guess overrides previous checkout.guess = false, complete refs and unique remote branches for DWIM' '
+	test_config checkout.guess false &&
+	test_completion "git checkout --guess " <<-\EOF
+	HEAD Z
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - a later --no-guess overrides previous checkout.guess = true, complete only refs' '
+	test_config checkout.guess true &&
+	test_completion "git checkout --no-guess " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with --detach, complete all references' '
+	test_completion "git switch --detach " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with --detach, complete only references' '
+	test_completion "git checkout --detach " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -d, complete all references' '
+	test_completion "git switch -d " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -d, complete only references' '
+	test_completion "git checkout -d " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with --track, complete only remote branches' '
+	test_completion "git switch --track " <<-\EOF
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with --track, complete only remote branches' '
+	test_completion "git checkout --track " <<-\EOF
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with --no-track, complete only local branch names' '
+	test_completion "git switch --no-track " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - with --no-track, complete only local references' '
+	test_completion "git checkout --no-track " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -c, complete all references' '
+	test_completion "git switch -c new-branch " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -C, complete all references' '
+	test_completion "git switch -C new-branch " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -c and --track, complete all references' '
+	test_completion "git switch -c new-branch --track " <<-EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -C and --track, complete all references' '
+	test_completion "git switch -C new-branch --track " <<-EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -c and --no-track, complete all references' '
+	test_completion "git switch -c new-branch --no-track " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - with -C and --no-track, complete all references' '
+	test_completion "git switch -C new-branch --no-track " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -b, complete all references' '
+	test_completion "git checkout -b new-branch " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -B, complete all references' '
+	test_completion "git checkout -B new-branch " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -b and --track, complete all references' '
+	test_completion "git checkout -b new-branch --track " <<-EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -B and --track, complete all references' '
+	test_completion "git checkout -B new-branch --track " <<-EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -b and --no-track, complete all references' '
+	test_completion "git checkout -b new-branch --no-track " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git checkout - with -B and --no-track, complete all references' '
+	test_completion "git checkout -B new-branch --no-track " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'git switch - for -c, complete local branches and unique remote branches' '
+	test_completion "git switch -c " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - for -C, complete local branches and unique remote branches' '
+	test_completion "git switch -C " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - for -c with --no-guess, complete local branches only' '
+	test_completion "git switch --no-guess -c " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - for -C with --no-guess, complete local branches only' '
+	test_completion "git switch --no-guess -C " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - for -c with --no-track, complete local branches only' '
+	test_completion "git switch --no-track -c " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - for -C with --no-track, complete local branches only' '
+	test_completion "git switch --no-track -C " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - for -b, complete local branches and unique remote branches' '
+	test_completion "git checkout -b " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - for -B, complete local branches and unique remote branches' '
+	test_completion "git checkout -B " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - for -b with --no-guess, complete local branches only' '
+	test_completion "git checkout --no-guess -b " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - for -B with --no-guess, complete local branches only' '
+	test_completion "git checkout --no-guess -B " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - for -b with --no-track, complete local branches only' '
+	test_completion "git checkout --no-track -b " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - for -B with --no-track, complete local branches only' '
+	test_completion "git checkout --no-track -B " <<-\EOF
+	main Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - with --orphan completes local branch names and unique remote branch names' '
+	test_completion "git switch --orphan " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git switch - --orphan with branch already provided completes nothing else' '
+	test_completion "git switch --orphan main " <<-\EOF
+
+	EOF
+'
+
+test_expect_success 'git checkout - with --orphan completes local branch names and unique remote branch names' '
+	test_completion "git checkout --orphan " <<-\EOF
+	branch-in-other Z
+	main Z
+	main-in-other Z
+	matching-branch Z
+	EOF
+'
+
+test_expect_success 'git checkout - --orphan with branch already provided completes local refs for a start-point' '
+	test_completion "git checkout --orphan main " <<-\EOF
+	HEAD Z
+	main Z
+	matching-branch Z
+	matching-tag Z
+	other/branch-in-other Z
+	other/main-in-other Z
+	EOF
+'
+
+test_expect_success 'teardown after ref completion' '
+	git branch -d matching-branch &&
+	git tag -d matching-tag &&
+	git remote remove other
+'
+
+test_expect_success 'basic' '
+	run_completion "git " &&
+	# built-in
+	grep -q "^add\$" out &&
+	# script
+	grep -q "^rebase\$" out &&
+	# plumbing
+	! grep -q "^ls-files\$" out &&
+
+	run_completion "git r" &&
+	! grep -q -v "^r" out
+'
+
+test_expect_success 'double dash "git" itself' '
+	test_completion "git --" <<-\EOF
+	--paginate
+	--no-pager
+	--git-dir
+	--bare
+	--version
+	--exec-path
+	--html-path
+	--man-path
+	--info-path
+	--work-tree
+	--namespace
+	--no-replace-objects
+	--help
+	EOF
+'
+
+test_expect_success 'double dash "git checkout"' '
+	test_completion "git checkout --" <<-\EOF
+	--quiet Z
+	--detach Z
+	--track Z
+	--orphan=Z
+	--ours Z
+	--theirs Z
+	--merge Z
+	--conflict=Z
+	--patch Z
+	--ignore-skip-worktree-bits Z
+	--ignore-other-worktrees Z
+	--recurse-submodules Z
+	--progress Z
+	--guess Z
+	--no-guess Z
+	--no-... Z
+	--overlay Z
+	--pathspec-file-nul Z
+	--pathspec-from-file=Z
+	EOF
+'
+
+test_expect_success 'general options' '
+	test_completion "git --ver" "--version" &&
+	test_completion "git --hel" "--help" &&
+	test_completion "git --exe" "--exec-path" &&
+	test_completion "git --htm" "--html-path" &&
+	test_completion "git --pag" "--paginate" &&
+	test_completion "git --no-p" "--no-pager" &&
+	test_completion "git --git" "--git-dir" &&
+	test_completion "git --wor" "--work-tree" &&
+	test_completion "git --nam" "--namespace" &&
+	test_completion "git --bar" "--bare" &&
+	test_completion "git --inf" "--info-path" &&
+	test_completion "git --no-r" "--no-replace-objects"
+'
+
+test_expect_failure 'general options plus command' '
+	test_completion "git --version check" "" &&
+	test_completion "git --paginate check" "checkout" &&
+	test_completion "git --git-dir=foo check" "checkout" &&
+	test_completion "git --bare check" "checkout" &&
+	test_completion "git --exec-path=foo check" "checkout" &&
+	test_completion "git --html-path check" "" &&
+	test_completion "git --no-pager check" "checkout" &&
+	test_completion "git --work-tree=foo check" "checkout" &&
+	test_completion "git --namespace=foo check" "checkout" &&
+	test_completion "git --paginate check" "checkout" &&
+	test_completion "git --info-path check" "" &&
+	test_completion "git --no-replace-objects check" "checkout" &&
+	test_completion "git --git-dir some/path check" "checkout" &&
+	test_completion "git -c conf.var=value check" "checkout" &&
+	test_completion "git -C some/path check" "checkout" &&
+	test_completion "git --work-tree some/path check" "checkout" &&
+	test_completion "git --namespace name/space check" "checkout"
+'
+
+test_expect_success 'git --help completion' '
+	test_completion "git --help ad" "add " &&
+	test_completion "git --help core" "core-tutorial "
+'
+
+test_expect_success 'setup for integration tests' '
+	echo content >file1 &&
+	echo more >file2 &&
+	git add file1 file2 &&
+	git commit -m one &&
+	git branch mybranch &&
+	git tag mytag
+'
+
+test_expect_success 'checkout completes ref names' '
+	test_completion "git checkout m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_failure 'git -C <path> checkout uses the right repo' '
+	test_completion "git -C subdir -C subsubdir -C .. -C ../otherrepo checkout b" <<-\EOF
+	branch-in-other Z
+	EOF
+'
+
+test_expect_success 'show completes all refs' '
+	test_completion "git show m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_success '<ref>: completes paths' '
+	test_completion "git show mytag:f" <<-\EOF
+	file1Z
+	file2Z
+	EOF
+'
+
+test_expect_success 'complete tree filename with spaces' '
+	echo content >"name with spaces" &&
+	git add "name with spaces" &&
+	git commit -m spaces &&
+	test_completion "git show HEAD:nam" <<-\EOF
+	name with spacesZ
+	EOF
+'
+
+test_expect_success 'complete tree filename with metacharacters' '
+	echo content >"name with \${meta}" &&
+	git add "name with \${meta}" &&
+	git commit -m meta &&
+	test_completion "git show HEAD:nam" <<-\EOF
+	name with ${meta}Z
+	name with spacesZ
+	EOF
+'
+
+test_expect_success PERL 'send-email' '
+	test_completion "git send-email --cov" <<-\EOF &&
+	--cover-from-description=Z
+	--cover-letter Z
+	EOF
+	test_completion "git send-email --val" <<-\EOF &&
+	--validate Z
+	EOF
+	test_completion "git send-email ma" "main "
+'
+
+test_expect_success 'complete files' '
+	git init tmp && cd tmp &&
+	test_when_finished "cd .. && rm -rf tmp" &&
+
+	echo "expected" > .gitignore &&
+	echo "out" >> .gitignore &&
+	echo "out_sorted" >> .gitignore &&
+
+	git add .gitignore &&
+	test_completion "git commit " ".gitignore" &&
+
+	git commit -m ignore &&
+
+	touch new &&
+	test_completion "git add " "new" &&
+
+	git add new &&
+	git commit -a -m new &&
+	test_completion "git add " "" &&
+
+	git mv new modified &&
+	echo modify > modified &&
+	test_completion "git add " "modified" &&
+
+	mkdir -p some/deep &&
+	touch some/deep/path &&
+	test_completion "git add some/" "some/deep" &&
+	git clean -f some &&
+
+	touch untracked &&
+
+	: TODO .gitignore should not be here &&
+	test_completion "git rm " <<-\EOF &&
+	.gitignore
+	modified
+	EOF
+
+	test_completion "git clean " "untracked" &&
+
+	: TODO .gitignore should not be here &&
+	test_completion "git mv " <<-\EOF &&
+	.gitignore
+	modified
+	EOF
+
+	mkdir dir &&
+	touch dir/file-in-dir &&
+	git add dir/file-in-dir &&
+	git commit -m dir &&
+
+	mkdir untracked-dir &&
+
+	: TODO .gitignore should not be here &&
+	test_completion "git mv modified " <<-\EOF &&
+	.gitignore
+	dir
+	modified
+	untracked
+	untracked-dir
+	EOF
+
+	test_completion "git commit " "modified" &&
+
+	: TODO .gitignore should not be here &&
+	test_completion "git ls-files " <<-\EOF &&
+	.gitignore
+	dir
+	modified
+	EOF
+
+	touch momified &&
+	test_completion "git add mom" "momified"
+'
+
+test_expect_success "simple alias" '
+	test_config alias.co checkout &&
+	test_completion "git co m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_success "recursive alias" '
+	test_config alias.co checkout &&
+	test_config alias.cod "co --detached" &&
+	test_completion "git cod m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_success "completion uses <cmd> completion for alias: !sh -c 'git <cmd> ...'" '
+	test_config alias.co "!sh -c '"'"'git checkout ...'"'"'" &&
+	test_completion "git co m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_success 'completion uses <cmd> completion for alias: !f () { VAR=val git <cmd> ... }' '
+	test_config alias.co "!f () { VAR=val git checkout ... ; } f" &&
+	test_completion "git co m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_success 'completion used <cmd> completion for alias: !f() { : git <cmd> ; ... }' '
+	test_config alias.co "!f() { : git checkout ; if ... } f" &&
+	test_completion "git co m" <<-\EOF
+	main Z
+	mybranch Z
+	mytag Z
+	EOF
+'
+
+test_expect_failure 'completion without explicit _git_xxx function' '
+	test_completion "git version --" <<-\EOF
+	--build-options Z
+	--no-build-options Z
+	EOF
+'
+
+test_expect_failure 'complete with tilde expansion' '
+	git init tmp && cd tmp &&
+	test_when_finished "cd .. && rm -rf tmp" &&
+
+	touch ~/tmp/file &&
+
+	test_completion "git add ~/tmp/" "~/tmp/file"
+'
+
+test_expect_success 'setup other remote for remote reference completion' '
+	git remote add other otherrepo &&
+	git fetch other
+'
+
+test_expect_success 'git config - section' '
+	test_completion "git config br" <<-\EOF
+	branch.Z
+	browser.Z
+	EOF
+'
+
+test_expect_success 'git config - section include, includeIf' '
+	test_completion "git config inclu" <<-\EOF
+	include.Z
+	includeIf.Z
+	EOF
+'
+
+test_expect_success 'git config - variable name' '
+	test_completion "git config log.d" <<-\EOF
+	log.date Z
+	log.decorate Z
+	log.diffMerges Z
+	EOF
+'
+
+test_expect_success 'git config - variable name include' '
+	test_completion "git config include.p" <<-\EOF
+	include.path Z
+	EOF
+'
+
+test_expect_success 'git config - value' '
+	test_completion "git config color.pager " <<-\EOF
+	false Z
+	true Z
+	EOF
+'
+
+test_expect_failure 'git -c - section' '
+	test_completion "git -c br" <<-\EOF
+	branch.Z
+	browser.Z
+	EOF
+'
+
+test_expect_failure 'git -c - variable name' '
+	test_completion "git -c log.d" <<-\EOF
+	log.date=Z
+	log.decorate=Z
+	log.diffMerges=Z
+	EOF
+'
+
+test_expect_failure 'git -c - value' '
+	test_completion "git -c color.pager=" <<-\EOF
+	false Z
+	true Z
+	EOF
+'
+
+test_expect_success 'git clone --config= - section' '
+	test_completion "git clone --config=br" <<-\EOF
+	branch.Z
+	browser.Z
+	EOF
+'
+
+test_expect_failure 'git clone --config= - variable name' '
+	test_completion "git clone --config=log.d" <<-\EOF
+	log.date=Z
+	log.decorate=Z
+	log.diffMerges=Z
+	EOF
+'
+
+test_expect_success 'git clone --config= - value' '
+	test_completion "git clone --config=color.pager=" <<-\EOF
+	false Z
+	true Z
+	EOF
+'
+
+test_expect_failure 'options with value' '
+	test_completion "git merge -X diff-algorithm=" <<-\EOF
+
+	EOF
+'
+
+test_done
diff --git a/t/t9904/.gitignore b/t/t9904/.gitignore
new file mode 100644
index 0000000000..f9917e1bf9
--- /dev/null
+++ b/t/t9904/.gitignore
@@ -0,0 +1 @@
+/.zcompdump
diff --git a/t/t9904/.zshrc b/t/t9904/.zshrc
new file mode 100644
index 0000000000..1da11a5445
--- /dev/null
+++ b/t/t9904/.zshrc
@@ -0,0 +1,50 @@
+setopt zle
+
+PS1="<PROMPT>"
+fpath=($ZDOTDIR $fpath)
+LISTMAX=1000
+
+autoload -U compinit && compinit -u
+
+zstyle ':completion:*:*:git:*' script "$GIT_BUILD_DIR/contrib/completion/git-completion.bash"
+zstyle ":completion:*:default" list-colors "no=<NO>" "fi=<NO>" "di=<NO>" "sp=<SP>" "lc=<LC>" "rc=<RC>" "ec=<EC>\n"
+zstyle ':completion:*' verbose no
+
+zle_complete () {
+	zle list-choices
+	zle kill-whole-line
+	print "<END-CHOICES>"
+}
+zle -N zle_complete
+bindkey "^I" zle_complete
+
+functions[_default]=:
+
+compadd () {
+	local pfx sfx
+	local -a args
+
+	if (( ${@[(I)-a|-d]} )); then
+		builtin compadd -V unsorted "$@"
+	else
+		while (($#)); do
+			case "$1" in
+			-p) pfx="$2" ; shift 2 ;;
+			-S) sfx="$2" ; shift 2 ;;
+			--) args+=($1) ; shift ; break ;;
+			*) args+=("$1") ; shift ;;
+			esac
+		done
+
+		while (($#)); do
+			args+=(${pfx}$1${sfx})
+			shift
+		done
+
+		builtin compadd -V unsorted -S '' "${args[@]}"
+	fi
+}
+
+_git_func () {
+	eval ${words[2,-2]}
+}
diff --git a/t/t9904/_git b/t/t9904/_git
new file mode 120000
index 0000000000..92d0240ac4
--- /dev/null
+++ b/t/t9904/_git
@@ -0,0 +1 @@
+../../contrib/completion/git-completion.zsh
\ No newline at end of file
diff --git a/t/t9904/completion b/t/t9904/completion
new file mode 100755
index 0000000000..2927b81f6a
--- /dev/null
+++ b/t/t9904/completion
@@ -0,0 +1,11 @@
+#!/bin/zsh
+
+zmodload zsh/zpty
+
+zpty zsh "ZDOTDIR=$(dirname $0) zsh -o NO_GLOBAL_RCS"
+zpty -n -w zsh "$1"$'\t'
+zpty -r zsh log '*<END-CHOICES>'
+
+for x in ${(M)${(f)log}:#*'<LC><NO>'*}; do
+	print -- "${${x%'<EC>'*}#*'<RC>'}"
+done
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 03/51] completion: fix __git_cmd_idx regression for zsh
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
  2022-08-30  9:30 ` [PATCH 01/51] test: completion add test for __git_cmd_idx Felipe Contreras
  2022-08-30  9:30 ` [PATCH 02/51] test: add zsh completion tests Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 04/51] completion: bash: trivial cleanup Felipe Contreras
                   ` (47 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras, Harrison McCullough

The commit 59d85a2a05 (git-completion.bash: use $__git_cmd_idx in more
places, 2021-04-22) caused a regression when using __git_complete and a
command relies on __git_cmd_idx. This was fixed in cea232194d
(completion: bash: fix late declaration of __git_cmd_idx, 2021-06-18)
but only for bash.

We need the function wrapper (__git_func_wrap in bash and _git in zsh)
to define __git_cmd_idx.

Otherwise the equivalent of __git_complete in zsh fails:

  compdef _git ga=git_add
  ga <tab>
  ga __git_find_on_cmdline:[:14: unknown condition: -lt

Reported-by: Harrison McCullough <mccullough.harrison@gmail.com>
Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 2 +-
 t/t9904-zsh-completion.sh             | 6 ++++++
 2 files changed, 7 insertions(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index cac6f61881..a1f2d27817 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -271,7 +271,7 @@ __git_zsh_main ()
 _git ()
 {
 	local _ret=1
-	local cur cword prev
+	local cur cword prev __git_cmd_idx=0
 
 	cur=${words[CURRENT]}
 	prev=${words[CURRENT-1]}
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 5179b2dc76..656eaf77ab 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -1121,4 +1121,10 @@ test_expect_failure 'options with value' '
 	EOF
 '
 
+test_expect_success 'main sets correct __git_cmd_idx' '
+	echo modified > file1 &&
+	touch file3 &&
+	test_completion "compdef _git ga=git_add${LF}ga --update f" "file1"
+'
+
 test_done
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 04/51] completion: bash: trivial cleanup
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (2 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 03/51] completion: fix __git_cmd_idx regression for zsh Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 05/51] completion: zsh: add higher-priority location Felipe Contreras
                   ` (46 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index ba5c395d2d..2df51ed946 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -3545,8 +3545,7 @@ fi
 
 __git_func_wrap ()
 {
-	local cur words cword prev
-	local __git_cmd_idx=0
+	local cur words cword prev __git_cmd_idx=0
 	_get_comp_words_by_ref -n =: cur words cword prev
 	$1
 }
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 05/51] completion: zsh: add higher-priority location
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (3 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 04/51] completion: bash: trivial cleanup Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 06/51] zsh: resolve symlink of script Felipe Contreras
                   ` (45 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

bash-completion looks in /usr/local/share first, we should too.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 1 +
 1 file changed, 1 insertion(+)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index a1f2d27817..535cf03176 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -35,6 +35,7 @@ if [ -z "$script" ]; then
 	locations=(
 		"$(dirname ${funcsourcetrace[1]%:*})"/git-completion.bash
 		"$HOME/.local/share/bash-completion/completions/git"
+		'/usr/local/share/bash-completion/completions/git'
 		"$bash_completion/git"
 		'/etc/bash_completion.d/git' # old debian
 		)
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 06/51] zsh: resolve symlink of script
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (4 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 05/51] completion: zsh: add higher-priority location Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 07/51] zsh: simplify realpath dirname idiom Felipe Contreras
                   ` (44 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Michael Bianco, Felipe Contreras

From: Michael Bianco <iloveitaly@gmail.com>

When using zinit the completions are symlinked to ~/.zinit/completions,
this causes the zsh script to not be able to find the bash script.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 535cf03176..1a405ba0a2 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -33,7 +33,7 @@ if [ -z "$script" ]; then
 		bash_completion='/usr/share/bash-completion/completions/'
 
 	locations=(
-		"$(dirname ${funcsourcetrace[1]%:*})"/git-completion.bash
+		"$(dirname $(realpath ${funcsourcetrace[1]%:*}))"/git-completion.bash
 		"$HOME/.local/share/bash-completion/completions/git"
 		'/usr/local/share/bash-completion/completions/git'
 		"$bash_completion/git"
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 07/51] zsh: simplify realpath dirname idiom
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (5 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 06/51] zsh: resolve symlink of script Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 08/51] test: reset environment variables Felipe Contreras
                   ` (43 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

There's a much simpler way in zsh.

It's a shame that ${0:A:h} doesn't work probably due to a bug in zsh.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 1a405ba0a2..18ad897568 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -33,7 +33,7 @@ if [ -z "$script" ]; then
 		bash_completion='/usr/share/bash-completion/completions/'
 
 	locations=(
-		"$(dirname $(realpath ${funcsourcetrace[1]%:*}))"/git-completion.bash
+		"${${funcsourcetrace[1]%:*}:A:h}"/git-completion.bash
 		"$HOME/.local/share/bash-completion/completions/git"
 		'/usr/local/share/bash-completion/completions/git'
 		"$bash_completion/git"
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 08/51] test: reset environment variables
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (6 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 07/51] zsh: simplify realpath dirname idiom Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 09/51] completion: prompt: use generic colors Felipe Contreras
                   ` (42 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

These should not affect the tests.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9903-bash-prompt.sh | 8 ++++++++
 1 file changed, 8 insertions(+)

diff --git a/t/t9903-bash-prompt.sh b/t/t9903-bash-prompt.sh
index 6a30f5719c..c94c351e23 100755
--- a/t/t9903-bash-prompt.sh
+++ b/t/t9903-bash-prompt.sh
@@ -18,6 +18,14 @@ c_green='\\[\\e[32m\\]'
 c_lblue='\\[\\e[1;34m\\]'
 c_clear='\\[\\e[0m\\]'
 
+unset GIT_PS1_SHOWDIRTYSTATE
+unset GIT_PS1_SHOWSTASHSTATE
+unset GIT_PS1_SHOWUNTRACKEDFILES
+unset GIT_PS1_COMPRESSSPARSESTATE
+unset GIT_PS1_SHOWUPSTREAM
+unset GIT_PS1_STATESEPARATOR
+unset GIT_PS1_SHOWCOLORHINTS
+
 test_expect_success 'setup for prompt tests' '
 	git init otherrepo &&
 	echo 1 >file &&
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 09/51] completion: prompt: use generic colors
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (7 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 08/51] test: reset environment variables Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 10/51] completion: fix for suboptions with value Felipe Contreras
                   ` (41 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

When the prompt command mode was introduced in 1bfc51ac81 (Allow
__git_ps1 to be used in PROMPT_COMMAND, 2012-10-10) the assumption was
that it was necessary in order to properly add colors to PS1 in bash,
but this wasn't true.

It's true that the \[ \] markers add the information needed to properly
calculate the width of the prompt, and they have to be added directly to
PS1, a function returning them doesn't work.

But that is because bash coverts the \[ \] markers in PS1 to \001 \002,
which is what readline ultimately needs in order to calculate the width.

We don't need bash to do this conversion, we can use \001 \002
ourselves, and then the prompt command mode is not necessary to display
colors.

This is what functions returning colors are supposed to do [1].

[1] http://mywiki.wooledge.org/BashFAQ/053

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-prompt.sh | 19 +++++++------------
 t/t9903-bash-prompt.sh           |  8 ++++----
 2 files changed, 11 insertions(+), 16 deletions(-)

diff --git a/contrib/completion/git-prompt.sh b/contrib/completion/git-prompt.sh
index 1435548e00..01bd807657 100644
--- a/contrib/completion/git-prompt.sh
+++ b/contrib/completion/git-prompt.sh
@@ -96,9 +96,7 @@
 #
 # If you would like a colored hint about the current dirty state, set
 # GIT_PS1_SHOWCOLORHINTS to a nonempty value. The colors are based on
-# the colored output of "git status -sb" and are available only when
-# using __git_ps1 for PROMPT_COMMAND or precmd in Bash,
-# but always available in Zsh.
+# the colored output of "git status -sb".
 #
 # If you would like __git_ps1 to do nothing in the case when the current
 # directory is set up to be ignored by git, then set
@@ -255,12 +253,12 @@ __git_ps1_colorize_gitstring ()
 		local c_lblue='%F{blue}'
 		local c_clear='%f'
 	else
-		# Using \[ and \] around colors is necessary to prevent
+		# Using \001 and \002 around colors is necessary to prevent
 		# issues with command line editing/browsing/completion!
-		local c_red='\[\e[31m\]'
-		local c_green='\[\e[32m\]'
-		local c_lblue='\[\e[1;34m\]'
-		local c_clear='\[\e[0m\]'
+		local c_red=$'\001\e[31m\002'
+		local c_green=$'\001\e[32m\002'
+		local c_lblue=$'\001\e[1;34m\002'
+		local c_clear=$'\001\e[0m\002'
 	fi
 	local bad_color=$c_red
 	local ok_color=$c_green
@@ -564,11 +562,8 @@ __git_ps1 ()
 		b="\${__git_ps1_branch_name}"
 	fi
 
-	# NO color option unless in PROMPT_COMMAND mode or it's Zsh
 	if [ -n "${GIT_PS1_SHOWCOLORHINTS-}" ]; then
-		if [ $pcmode = yes ] || [ -n "${ZSH_VERSION-}" ]; then
-			__git_ps1_colorize_gitstring
-		fi
+		__git_ps1_colorize_gitstring
 	fi
 
 	local f="$h$w$i$s$u$p"
diff --git a/t/t9903-bash-prompt.sh b/t/t9903-bash-prompt.sh
index c94c351e23..fb396ff3a7 100755
--- a/t/t9903-bash-prompt.sh
+++ b/t/t9903-bash-prompt.sh
@@ -13,10 +13,10 @@ export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME
 . "$GIT_BUILD_DIR/contrib/completion/git-prompt.sh"
 
 actual="$TRASH_DIRECTORY/actual"
-c_red='\\[\\e[31m\\]'
-c_green='\\[\\e[32m\\]'
-c_lblue='\\[\\e[1;34m\\]'
-c_clear='\\[\\e[0m\\]'
+c_red='\001\e[31m\002'
+c_green='\001\e[32m\002'
+c_lblue='\001\e[1;34m\002'
+c_clear='\001\e[0m\002'
 
 unset GIT_PS1_SHOWDIRTYSTATE
 unset GIT_PS1_SHOWSTASHSTATE
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 10/51] completion: fix for suboptions with value
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (8 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 09/51] completion: prompt: use generic colors Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 11/51] completion: zsh: trivial improvement Felipe Contreras
                   ` (40 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

We need to ignore options that don't start with -- as well.

Depending on the value of COMP_WORDBREAKS, the last word could be
duplicated otherwise.

Can be tested with:

  git merge -X diff-algorithm=<tab>

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 2 +-
 t/t9904-zsh-completion.sh             | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 18ad897568..1905ff98b7 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -56,7 +56,7 @@ __gitcomp ()
 	local cur_="${3-$cur}"
 
 	case "$cur_" in
-	--*=)
+	*=)
 		;;
 	--no-*)
 		local c IFS=$' \t\n'
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 656eaf77ab..d3fe42a9b3 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -157,7 +157,7 @@ test_expect_success '__gitcomp - expand/narrow all negative options' '
 	EOF
 '
 
-test_expect_failure '__gitcomp - equal skip' '
+test_expect_success '__gitcomp - equal skip' '
 	test_gitcomp "--option=" "--option=" <<-\EOF &&
 
 	EOF
@@ -1115,7 +1115,7 @@ test_expect_success 'git clone --config= - value' '
 	EOF
 '
 
-test_expect_failure 'options with value' '
+test_expect_success 'options with value' '
 	test_completion "git merge -X diff-algorithm=" <<-\EOF
 
 	EOF
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 11/51] completion: zsh: trivial improvement
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (9 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 10/51] completion: fix for suboptions with value Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:30 ` [PATCH 12/51] completion: bash: do not modify COMP_WORDBREAKS Felipe Contreras
                   ` (39 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

$words has basically all the words we need, except the first one: git.

Lets simply add that instead of passing the original, which contains
options we don't want to pass downstream (like -c and -C).

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 5 +----
 1 file changed, 1 insertion(+), 4 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 1905ff98b7..4d81ca73b5 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -220,9 +220,6 @@ __git_zsh_main ()
 {
 	local curcontext="$curcontext" state state_descr line
 	typeset -A opt_args
-	local -a orig_words
-
-	orig_words=( ${words[@]} )
 
 	_arguments -C \
 		'(-p --paginate --no-pager)'{-p,--paginate}'[pipe all output into ''less'']' \
@@ -262,7 +259,7 @@ __git_zsh_main ()
 
 		(( $+opt_args[--help] )) && command='help'
 
-		words=( ${orig_words[@]} )
+		words=( git ${words[@]} )
 
 		__git_zsh_bash_func $command
 		;;
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 12/51] completion: bash: do not modify COMP_WORDBREAKS
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (10 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 11/51] completion: zsh: trivial improvement Felipe Contreras
@ 2022-08-30  9:30 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 13/51] test: completion: fix currently typed words Felipe Contreras
                   ` (38 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:30 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

There was no need for this once __git_reassemble_comp_words_by_ref() was
introduced. Now irrespective of the value of COMP_WORDBREAKS, words are
always joined together.

By default COMP_WORDBREAKS does contain a colon, and if it doesn't
somebody probably has a reason for it.

Completions are not supposed to modify COMP_WORDBREAKS and none of the
completions in the bash-completion project do.

We manually set it in Zsh so the Bash script is not confused.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 5 -----
 contrib/completion/git-completion.zsh  | 1 +
 2 files changed, 1 insertion(+), 5 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 2df51ed946..ef0b7aa192 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -59,11 +59,6 @@
 #     When set to "1" suggest all options, including options which are
 #     typically hidden (e.g. '--allow-empty' for 'git commit').
 
-case "$COMP_WORDBREAKS" in
-*:*) : great ;;
-*)   COMP_WORDBREAKS="$COMP_WORDBREAKS:"
-esac
-
 # Discovers the path to the git repository taking any '--git-dir=<path>' and
 # '-C <path>' options into account and stores it in the $__git_repo_path
 # variable.
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 4d81ca73b5..2de1a72c09 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -46,6 +46,7 @@ fi
 
 local old_complete="$functions[complete]"
 functions[complete]=:
+COMP_WORDBREAKS=':'
 GIT_SOURCING_ZSH_COMPLETION=y . "$script"
 functions[complete]="$old_complete"
 
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 13/51] test: completion: fix currently typed words
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (11 preceding siblings ...)
  2022-08-30  9:30 ` [PATCH 12/51] completion: bash: do not modify COMP_WORDBREAKS Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 14/51] test: completion: switch __gitcomp_nl prefix test Felipe Contreras
                   ` (37 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

They don't match what we are supposed to be completing.

No functional changes.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9902-completion.sh     | 4 ++--
 t/t9904-zsh-completion.sh | 4 ++--
 2 files changed, 4 insertions(+), 4 deletions(-)

diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index 8cc30448c7..031f05cf47 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -486,7 +486,7 @@ test_expect_success '__gitcomp - option parameter' '
 '
 
 test_expect_success '__gitcomp - prefix' '
-	test_gitcomp "branch.me" "remote merge mergeoptions rebase" \
+	test_gitcomp "branch.maint.me" "remote merge mergeoptions rebase" \
 		"branch.maint." "me" <<-\EOF
 	branch.maint.merge Z
 	branch.maint.mergeoptions Z
@@ -494,7 +494,7 @@ test_expect_success '__gitcomp - prefix' '
 '
 
 test_expect_success '__gitcomp - suffix' '
-	test_gitcomp "branch.me" "master maint next seen" "branch." \
+	test_gitcomp "branch.ma" "master maint next seen" "branch." \
 		"ma" "." <<-\EOF
 	branch.master.Z
 	branch.maint.Z
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index d3fe42a9b3..e9df29c135 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -106,7 +106,7 @@ test_expect_success '__gitcomp - option parameter' '
 '
 
 test_expect_failure '__gitcomp - prefix' '
-	test_gitcomp "branch.me" "remote merge mergeoptions rebase" \
+	test_gitcomp "branch.maint.me" "remote merge mergeoptions rebase" \
 		"branch.maint." "me" <<-\EOF
 	branch.maint.merge Z
 	branch.maint.mergeoptions Z
@@ -114,7 +114,7 @@ test_expect_failure '__gitcomp - prefix' '
 '
 
 test_expect_failure '__gitcomp - suffix' '
-	test_gitcomp "branch.me" "master maint next seen" "branch." \
+	test_gitcomp "branch.ma" "master maint next seen" "branch." \
 		"ma" "." <<-\EOF
 	branch.master.Z
 	branch.maint.Z
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 14/51] test: completion: switch __gitcomp_nl prefix test
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (12 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 13/51] test: completion: fix currently typed words Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 15/51] test: completion: add run_func() helper Felipe Contreras
                   ` (36 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

By default COMP_WORDBREAKS includes =, so it's not realistic to test for
a prefix that almost never will be there.

In bash there are no functional changes, but in zsh this makes the test
pass.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9902-completion.sh     | 6 +++---
 t/t9904-zsh-completion.sh | 8 ++++----
 2 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index 031f05cf47..2fe056ab59 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -565,9 +565,9 @@ test_expect_success '__gitcomp_nl - trailing space' '
 '
 
 test_expect_success '__gitcomp_nl - prefix' '
-	test_gitcomp_nl "--fixup=m" "$refs" "--fixup=" "m" <<-EOF
-	--fixup=main Z
-	--fixup=maint Z
+	test_gitcomp_nl "branch.m" "$refs" "branch." "m" <<-EOF
+	branch.main Z
+	branch.maint Z
 	EOF
 '
 
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index e9df29c135..dbd0671ab6 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -180,10 +180,10 @@ test_expect_success '__gitcomp_nl - trailing space' '
 	EOF
 '
 
-test_expect_failure '__gitcomp_nl - prefix' '
-	test_gitcomp_nl "--fixup=m" "$refs" "--fixup=" "m" <<-EOF
-	--fixup=main Z
-	--fixup=maint Z
+test_expect_success '__gitcomp_nl - prefix' '
+	test_gitcomp_nl "branch.m" "$refs" "branch." "m" <<-EOF
+	branch.main Z
+	branch.maint Z
 	EOF
 '
 
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 15/51] test: completion: add run_func() helper
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (13 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 14/51] test: completion: switch __gitcomp_nl prefix test Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 16/51] completion: bash: remove non-append functionality Felipe Contreras
                   ` (35 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Pretty straightforward: runs functions.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9902-completion.sh | 58 ++++++++++++++++++-------------------------
 1 file changed, 24 insertions(+), 34 deletions(-)

diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index 2fe056ab59..91dfb618c1 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -75,6 +75,12 @@ run_completion ()
 	__git_wrap__git_main && print_comp
 }
 
+run_func ()
+{
+	local -a COMPREPLY &&
+	"$@" && print_comp
+}
+
 # Test high-level completion
 # Arguments are:
 # 1: typed text so far (cur)
@@ -452,8 +458,7 @@ test_expect_success '__gitcomp_direct - puts everything into COMPREPLY as-is' '
 	EOF
 	(
 		cur=should_be_ignored &&
-		__gitcomp_direct "$(cat expected)" &&
-		print_comp
+		run_func __gitcomp_direct "$(cat expected)"
 	) &&
 	test_cmp expected out
 '
@@ -547,7 +552,7 @@ test_expect_success '__gitcomp - equal skip' '
 '
 
 test_expect_success '__gitcomp - doesnt fail because of invalid variable name' '
-	__gitcomp "$invalid_variable_name"
+	run_func __gitcomp "$invalid_variable_name"
 '
 
 read -r -d "" refs <<-\EOF
@@ -586,7 +591,7 @@ test_expect_success '__gitcomp_nl - no suffix' '
 '
 
 test_expect_success '__gitcomp_nl - doesnt fail because of invalid variable name' '
-	__gitcomp_nl "$invalid_variable_name"
+	run_func __gitcomp_nl "$invalid_variable_name"
 '
 
 test_expect_success '__git_remotes - list remotes from $GIT_DIR/remotes and from config file' '
@@ -1087,8 +1092,7 @@ test_expect_success '__git_complete_refs - simple' '
 	EOF
 	(
 		cur= &&
-		__git_complete_refs &&
-		print_comp
+		run_func __git_complete_refs
 	) &&
 	test_cmp expected out
 '
@@ -1100,8 +1104,7 @@ test_expect_success '__git_complete_refs - matching' '
 	EOF
 	(
 		cur=mat &&
-		__git_complete_refs &&
-		print_comp
+		run_func __git_complete_refs
 	) &&
 	test_cmp expected out
 '
@@ -1114,8 +1117,7 @@ test_expect_success '__git_complete_refs - remote' '
 	EOF
 	(
 		cur= &&
-		__git_complete_refs --remote=other &&
-		print_comp
+		run_func __git_complete_refs --remote=other
 	) &&
 	test_cmp expected out
 '
@@ -1133,8 +1135,7 @@ test_expect_success '__git_complete_refs - track' '
 	EOF
 	(
 		cur= &&
-		__git_complete_refs --track &&
-		print_comp
+		run_func __git_complete_refs --track
 	) &&
 	test_cmp expected out
 '
@@ -1146,8 +1147,7 @@ test_expect_success '__git_complete_refs - current word' '
 	EOF
 	(
 		cur="--option=mat" &&
-		__git_complete_refs --cur="${cur#*=}" &&
-		print_comp
+		run_func __git_complete_refs --cur="${cur#*=}"
 	) &&
 	test_cmp expected out
 '
@@ -1159,8 +1159,7 @@ test_expect_success '__git_complete_refs - prefix' '
 	EOF
 	(
 		cur=v1.0..mat &&
-		__git_complete_refs --pfx=v1.0.. --cur=mat &&
-		print_comp
+		run_func __git_complete_refs --pfx=v1.0.. --cur=mat
 	) &&
 	test_cmp expected out
 '
@@ -1176,8 +1175,7 @@ test_expect_success '__git_complete_refs - suffix' '
 	EOF
 	(
 		cur= &&
-		__git_complete_refs --sfx=. &&
-		print_comp
+		run_func __git_complete_refs --sfx=.
 	) &&
 	test_cmp expected out
 '
@@ -1190,8 +1188,7 @@ test_expect_success '__git_complete_fetch_refspecs - simple' '
 	EOF
 	(
 		cur= &&
-		__git_complete_fetch_refspecs other &&
-		print_comp
+		run_func __git_complete_fetch_refspecs other
 	) &&
 	test_cmp expected out
 '
@@ -1202,8 +1199,7 @@ test_expect_success '__git_complete_fetch_refspecs - matching' '
 	EOF
 	(
 		cur=br &&
-		__git_complete_fetch_refspecs other "" br &&
-		print_comp
+		run_func __git_complete_fetch_refspecs other "" br
 	) &&
 	test_cmp expected out
 '
@@ -1216,8 +1212,7 @@ test_expect_success '__git_complete_fetch_refspecs - prefix' '
 	EOF
 	(
 		cur="+" &&
-		__git_complete_fetch_refspecs other "+" ""  &&
-		print_comp
+		run_func __git_complete_fetch_refspecs other "+" ""
 	) &&
 	test_cmp expected out
 '
@@ -1230,8 +1225,7 @@ test_expect_success '__git_complete_fetch_refspecs - fully qualified' '
 	EOF
 	(
 		cur=refs/ &&
-		__git_complete_fetch_refspecs other "" refs/ &&
-		print_comp
+		run_func __git_complete_fetch_refspecs other "" refs/
 	) &&
 	test_cmp expected out
 '
@@ -1244,8 +1238,7 @@ test_expect_success '__git_complete_fetch_refspecs - fully qualified & prefix' '
 	EOF
 	(
 		cur=+refs/ &&
-		__git_complete_fetch_refspecs other + refs/ &&
-		print_comp
+		run_func __git_complete_fetch_refspecs other + refs/
 	) &&
 	test_cmp expected out
 '
@@ -1931,8 +1924,7 @@ test_path_completion ()
 		# unusual characters in path names.  By requesting only
 		# untracked files we do not have to bother adding any
 		# paths to the index in those tests.
-		__git_complete_index_file --others &&
-		print_comp
+		run_func __git_complete_index_file --others
 	) &&
 	test_cmp expected out
 }
@@ -2457,8 +2449,7 @@ do
 			words=(git push '$flag' other ma) &&
 			cword=${#words[@]} cur=${words[cword-1]} &&
 			__git_cmd_idx=1 &&
-			__git_complete_remote_or_refspec &&
-			print_comp
+			run_func __git_complete_remote_or_refspec
 		) &&
 		test_cmp expected out
 	'
@@ -2471,8 +2462,7 @@ do
 			words=(git push other '$flag' ma) &&
 			cword=${#words[@]} cur=${words[cword-1]} &&
 			__git_cmd_idx=1 &&
-			__git_complete_remote_or_refspec &&
-			print_comp
+			run_func __git_complete_remote_or_refspec
 		) &&
 		test_cmp expected out
 	'
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 16/51] completion: bash: remove non-append functionality
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (14 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 15/51] test: completion: add run_func() helper Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 17/51] completion: bash: get rid of _append() functions Felipe Contreras
                   ` (34 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

There's no point in setting COMPREPLY only to override it later, and in
fact... we don't do that.

Therefore there's no functional difference between __gitcomp_direct()
and __gitcomp_direct_append(), since __gitcomp_direct() *always*
operates on empty COMPREPLY.

The same goes for __gitcomp_nl().

This patch makes the functionality of append and non-append functions
the same.

No functional changes.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index ef0b7aa192..6571dc1b2d 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -312,7 +312,7 @@ __gitcomp_direct ()
 {
 	local IFS=$'\n'
 
-	COMPREPLY=($1)
+	COMPREPLY+=($1)
 }
 
 # Similar to __gitcomp_direct, but appends to COMPREPLY instead.
@@ -464,7 +464,6 @@ __gitcomp_nl_append ()
 #    appended.
 __gitcomp_nl ()
 {
-	COMPREPLY=()
 	__gitcomp_nl_append "$@"
 }
 
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 17/51] completion: bash: get rid of _append() functions
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (15 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 16/51] completion: bash: remove non-append functionality Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 18/51] completion: bash: get rid of any non-append code Felipe Contreras
                   ` (33 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

There's no need to have duplicated functionality.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 35 ++++++--------------------
 contrib/completion/git-completion.zsh  | 10 --------
 2 files changed, 7 insertions(+), 38 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 6571dc1b2d..4a7e75b48d 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -301,8 +301,7 @@ _get_comp_words_by_ref ()
 }
 fi
 
-# Fills the COMPREPLY array with prefiltered words without any additional
-# processing.
+# Appends prefiltered words to COMPREPLY without any additional processing.
 # Callers must take care of providing only words that match the current word
 # to be completed and adding any prefix and/or suffix (trailing space!), if
 # necessary.
@@ -315,19 +314,6 @@ __gitcomp_direct ()
 	COMPREPLY+=($1)
 }
 
-# Similar to __gitcomp_direct, but appends to COMPREPLY instead.
-# Callers must take care of providing only words that match the current word
-# to be completed and adding any prefix and/or suffix (trailing space!), if
-# necessary.
-# 1: List of newline-separated matching completion words, complete with
-#    prefix and suffix.
-__gitcomp_direct_append ()
-{
-	local IFS=$'\n'
-
-	COMPREPLY+=($1)
-}
-
 __gitcompappend ()
 {
 	local x i=${#COMPREPLY[@]}
@@ -445,16 +431,8 @@ __gitcomp_builtin ()
 	__gitcomp "$options"
 }
 
-# Variation of __gitcomp_nl () that appends to the existing list of
-# completion candidates, COMPREPLY.
-__gitcomp_nl_append ()
-{
-	local IFS=$'\n'
-	__gitcompappend "$1" "${2-}" "${3-$cur}" "${4- }"
-}
-
 # Generates completion reply from newline-separated possible completion words
-# by appending a space to all of them.
+# by appending a space to all of them. The result is appended to COMPREPLY.
 # It accepts 1 to 4 arguments:
 # 1: List of possible completion words, separated by a single newline.
 # 2: A prefix to be added to each possible completion word (optional).
@@ -464,7 +442,8 @@ __gitcomp_nl_append ()
 #    appended.
 __gitcomp_nl ()
 {
-	__gitcomp_nl_append "$@"
+	local IFS=$'\n'
+	__gitcompappend "$1" "${2-}" "${3-$cur}" "${4- }"
 }
 
 # Fills the COMPREPLY array with prefiltered paths without any additional
@@ -851,7 +830,7 @@ __git_complete_refs ()
 
 	# Append DWIM remote branch names if requested
 	if [ "$dwim" = "yes" ]; then
-		__gitcomp_direct_append "$(__git_dwim_remote_heads "$pfx" "$cur_" "$sfx")"
+		__gitcomp_direct "$(__git_dwim_remote_heads "$pfx" "$cur_" "$sfx")"
 	fi
 }
 
@@ -2650,7 +2629,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__gitcomp_direct "$(__git_heads "$pfx" "$cur_" ".")"
-		__gitcomp_nl_append $'autoSetupMerge\nautoSetupRebase\n' "$pfx" "$cur_" "${sfx- }"
+		__gitcomp_nl $'autoSetupMerge\nautoSetupRebase\n' "$pfx" "$cur_" "${sfx- }"
 		return
 		;;
 	guitool.*.*)
@@ -2700,7 +2679,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__gitcomp_nl "$(__git_remotes)" "$pfx" "$cur_" "."
-		__gitcomp_nl_append "pushDefault" "$pfx" "$cur_" "${sfx- }"
+		__gitcomp_nl "pushDefault" "$pfx" "$cur_" "${sfx- }"
 		return
 		;;
 	url.*.*)
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 2de1a72c09..35300a08cd 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -122,16 +122,6 @@ __gitcomp_file ()
 	compadd -f -p "${2-}" -- ${(f)1} && _ret=0
 }
 
-__gitcomp_direct_append ()
-{
-	__gitcomp_direct "$@"
-}
-
-__gitcomp_nl_append ()
-{
-	__gitcomp_nl "$@"
-}
-
 __gitcomp_file_direct ()
 {
 	__gitcomp_file "$1" ""
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 18/51] completion: bash: get rid of any non-append code
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (16 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 17/51] completion: bash: get rid of _append() functions Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 19/51] completion: zsh: fix options with arguments Felipe Contreras
                   ` (32 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 12 +++---------
 1 file changed, 3 insertions(+), 9 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 4a7e75b48d..ed126bbec4 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -314,7 +314,7 @@ __gitcomp_direct ()
 	COMPREPLY+=($1)
 }
 
-__gitcompappend ()
+__gitcompadd ()
 {
 	local x i=${#COMPREPLY[@]}
 	for x in $1; do
@@ -324,12 +324,6 @@ __gitcompappend ()
 	done
 }
 
-__gitcompadd ()
-{
-	COMPREPLY=()
-	__gitcompappend "$@"
-}
-
 # Generates completion reply, appending a space to possible completion words,
 # if necessary.
 # It accepts 1 to 4 arguments:
@@ -443,7 +437,7 @@ __gitcomp_builtin ()
 __gitcomp_nl ()
 {
 	local IFS=$'\n'
-	__gitcompappend "$1" "${2-}" "${3-$cur}" "${4- }"
+	__gitcompadd "$1" "${2-}" "${3-$cur}" "${4- }"
 }
 
 # Fills the COMPREPLY array with prefiltered paths without any additional
@@ -456,7 +450,7 @@ __gitcomp_file_direct ()
 {
 	local IFS=$'\n'
 
-	COMPREPLY=($1)
+	COMPREPLY+=($1)
 
 	# use a hack to enable file mode in bash < 4
 	compopt -o filenames +o nospace 2>/dev/null ||
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 19/51] completion: zsh: fix options with arguments
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (17 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 18/51] completion: bash: get rid of any non-append code Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 20/51] completion: zsh: expand --git-dir file argument Felipe Contreras
                   ` (31 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

They support both '--git-dir=value' and '--git-dir value'. Fix the
arguments to support both.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 8 ++++----
 1 file changed, 4 insertions(+), 4 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 35300a08cd..10ad15face 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -215,15 +215,15 @@ __git_zsh_main ()
 	_arguments -C \
 		'(-p --paginate --no-pager)'{-p,--paginate}'[pipe all output into ''less'']' \
 		'(-p --paginate)--no-pager[do not pipe git output into a pager]' \
-		'--git-dir=-[set the path to the repository]: :_directories' \
+		'--git-dir=[set the path to the repository]: :_directories' \
 		'--bare[treat the repository as a bare repository]' \
 		'(- :)--version[prints the git suite version]' \
-		'--exec-path=-[path to where your core git programs are installed]:: :_directories' \
+		'--exec-path=[path to where your core git programs are installed]:: :_directories' \
 		'--html-path[print the path where git''s HTML documentation is installed]' \
 		'--info-path[print the path where the Info files are installed]' \
 		'--man-path[print the manpath (see `man(1)`) for the man pages]' \
-		'--work-tree=-[set the path to the working tree]: :_directories' \
-		'--namespace=-[set the git namespace]' \
+		'--work-tree=[set the path to the working tree]: :_directories' \
+		'--namespace=[set the git namespace]:' \
 		'--no-replace-objects[do not use replacement refs to replace git objects]' \
 		'(- :)--help[prints the synopsis and a list of the most commonly used commands]: :->arg' \
 		'(-): :->command' \
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 20/51] completion: zsh: expand --git-dir file argument
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (18 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 19/51] completion: zsh: fix options with arguments Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 21/51] completion: zsh: add support for general -C opts Felipe Contreras
                   ` (30 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 10ad15face..0e72b9add7 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -245,7 +245,7 @@ __git_zsh_main ()
 		if (( $+opt_args[--bare] )); then
 			__git_dir='.'
 		else
-			__git_dir=${opt_args[--git-dir]}
+			__git_dir=${~opt_args[--git-dir]}
 		fi
 
 		(( $+opt_args[--help] )) && command='help'
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 21/51] completion: zsh: add support for general -C opts
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (19 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 20/51] completion: zsh: expand --git-dir file argument Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 22/51] completion: zsh: fix for undefined completions Felipe Contreras
                   ` (29 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 6 ++++++
 t/t9904-zsh-completion.sh             | 2 +-
 2 files changed, 7 insertions(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 0e72b9add7..e771a2a53a 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -211,6 +211,7 @@ __git_zsh_main ()
 {
 	local curcontext="$curcontext" state state_descr line
 	typeset -A opt_args
+	local -a __git_C_args
 
 	_arguments -C \
 		'(-p --paginate --no-pager)'{-p,--paginate}'[pipe all output into ''less'']' \
@@ -226,6 +227,7 @@ __git_zsh_main ()
 		'--namespace=[set the git namespace]:' \
 		'--no-replace-objects[do not use replacement refs to replace git objects]' \
 		'(- :)--help[prints the synopsis and a list of the most commonly used commands]: :->arg' \
+		'*-C[run as if git was started in the given path]: :_directories' \
 		'(-): :->command' \
 		'(-)*:: :->arg' && return
 
@@ -248,6 +250,10 @@ __git_zsh_main ()
 			__git_dir=${~opt_args[--git-dir]}
 		fi
 
+		for x in ${(s.:.)opt_args[-C]}; do
+			__git_C_args+=('-C' ${~x})
+		done
+
 		(( $+opt_args[--help] )) && command='help'
 
 		words=( git ${words[@]} )
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index dbd0671ab6..cd223b6e2a 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -844,7 +844,7 @@ test_expect_success 'checkout completes ref names' '
 	EOF
 '
 
-test_expect_failure 'git -C <path> checkout uses the right repo' '
+test_expect_success 'git -C <path> checkout uses the right repo' '
 	test_completion "git -C subdir -C subsubdir -C .. -C ../otherrepo checkout b" <<-\EOF
 	branch-in-other Z
 	EOF
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 22/51] completion: zsh: fix for undefined completions
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (20 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 21/51] completion: zsh: add support for general -C opts Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 23/51] completion: zsh: add support for general -c opts Felipe Contreras
                   ` (28 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

The parseopt helper can generate the completions even if the function is
unspecified.

  git version --<tab>

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 3 +++
 t/t9904-zsh-completion.sh             | 2 +-
 2 files changed, 4 insertions(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index e771a2a53a..30607aa93d 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -141,6 +141,9 @@ __git_complete_command ()
 	if (( $+functions[$completion_func] )); then
 		emulate ksh -c $completion_func
 		return 0
+	elif emulate ksh -c "__git_support_parseopt_helper $command"; then
+		emulate ksh -c "__git_complete_common $command"
+		return 0
 	else
 		return 1
 	fi
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index cd223b6e2a..14f5e5d9b8 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -1015,7 +1015,7 @@ test_expect_success 'completion used <cmd> completion for alias: !f() { : git <c
 	EOF
 '
 
-test_expect_failure 'completion without explicit _git_xxx function' '
+test_expect_success 'completion without explicit _git_xxx function' '
 	test_completion "git version --" <<-\EOF
 	--build-options Z
 	--no-build-options Z
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 23/51] completion: zsh: add support for general -c opts
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (21 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 22/51] completion: zsh: fix for undefined completions Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 24/51] completion: zsh: fix extra space on foo= Felipe Contreras
                   ` (27 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

So we can specify configurations.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 5 +++++
 t/t9904-zsh-completion.sh             | 4 ++--
 2 files changed, 7 insertions(+), 2 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 30607aa93d..b062090a13 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -231,6 +231,7 @@ __git_zsh_main ()
 		'--no-replace-objects[do not use replacement refs to replace git objects]' \
 		'(- :)--help[prints the synopsis and a list of the most commonly used commands]: :->arg' \
 		'*-C[run as if git was started in the given path]: :_directories' \
+		'*-c[pass a configuration parameter to the command]: :->config' \
 		'(-): :->command' \
 		'(-)*:: :->arg' && return
 
@@ -244,6 +245,10 @@ __git_zsh_main ()
 			let _ret || break
 		done
 		;;
+	(config)
+		compset -P '*[=:]'
+		emulate ksh -c __git_complete_config_variable_name_and_value
+		;;
 	(arg)
 		local command="${words[1]}" __git_dir __git_cmd_idx=1
 
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 14f5e5d9b8..4c7cf4234e 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -1071,7 +1071,7 @@ test_expect_success 'git config - value' '
 	EOF
 '
 
-test_expect_failure 'git -c - section' '
+test_expect_success 'git -c - section' '
 	test_completion "git -c br" <<-\EOF
 	branch.Z
 	browser.Z
@@ -1086,7 +1086,7 @@ test_expect_failure 'git -c - variable name' '
 	EOF
 '
 
-test_expect_failure 'git -c - value' '
+test_expect_success 'git -c - value' '
 	test_completion "git -c color.pager=" <<-\EOF
 	false Z
 	true Z
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 24/51] completion: zsh: fix extra space on foo=
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (22 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 23/51] completion: zsh: add support for general -c opts Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 25/51] completion: zsh: add excluded options Felipe Contreras
                   ` (26 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Upstream commit e1e00089da fixed the issue for Bash, but not for Zsh.

When we are typing configurations an = at the end signifies we still
want to type the value.

Can be tested with:

  git -c log.d<tab>

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 2 +-
 t/t9904-zsh-completion.sh             | 4 ++--
 2 files changed, 3 insertions(+), 3 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index b062090a13..f732881958 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -87,7 +87,7 @@ __gitcomp ()
 			fi
 			c="$c${4-}"
 			case $c in
-			--*=|*.) ;;
+			*=|*.) ;;
 			*) c="$c " ;;
 			esac
 			array+=("$c")
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 4c7cf4234e..7283af3342 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -1078,7 +1078,7 @@ test_expect_success 'git -c - section' '
 	EOF
 '
 
-test_expect_failure 'git -c - variable name' '
+test_expect_success 'git -c - variable name' '
 	test_completion "git -c log.d" <<-\EOF
 	log.date=Z
 	log.decorate=Z
@@ -1100,7 +1100,7 @@ test_expect_success 'git clone --config= - section' '
 	EOF
 '
 
-test_expect_failure 'git clone --config= - variable name' '
+test_expect_success 'git clone --config= - variable name' '
 	test_completion "git clone --config=log.d" <<-\EOF
 	log.date=Z
 	log.decorate=Z
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 25/51] completion: zsh: add excluded options
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (23 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 24/51] completion: zsh: fix extra space on foo= Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 26/51] completion: zsh: always set compset Felipe Contreras
                   ` (25 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Add more excluded options, for example: --bare excludes --git-dir.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 17 +++++++++--------
 t/t9904-zsh-completion.sh             |  2 +-
 2 files changed, 10 insertions(+), 9 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index f732881958..d2eb221d79 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -217,15 +217,16 @@ __git_zsh_main ()
 	local -a __git_C_args
 
 	_arguments -C \
-		'(-p --paginate --no-pager)'{-p,--paginate}'[pipe all output into ''less'']' \
-		'(-p --paginate)--no-pager[do not pipe git output into a pager]' \
-		'--git-dir=[set the path to the repository]: :_directories' \
-		'--bare[treat the repository as a bare repository]' \
+		'(-p --paginate -P --no-pager)'{-p,--paginate}'[pipe all output into ''less'']' \
+		'(-p --paginate -P --no-pager)'{-P,--no-pager}'[do not pipe git output into a pager]' \
+		'(--bare)--git-dir=[set the path to the repository]: :_directories' \
+		'(--git-dir)--bare[treat the repository as a bare repository]' \
 		'(- :)--version[prints the git suite version]' \
-		'--exec-path=[path to where your core git programs are installed]:: :_directories' \
-		'--html-path[print the path where git''s HTML documentation is installed]' \
-		'--info-path[print the path where the Info files are installed]' \
-		'--man-path[print the manpath (see `man(1)`) for the man pages]' \
+		'--exec-path=[path to where your core git programs are installed]: :_directories' \
+		'(- :)--exec-path[print the path where your core git programs are installed]' \
+		'(- :)--html-path[print the path where git''s HTML documentation is installed]' \
+		'(- :)--info-path[print the path where the Info files are installed]' \
+		'(- :)--man-path[print the manpath (see `man(1)`) for the man pages]' \
 		'--work-tree=[set the path to the working tree]: :_directories' \
 		'--namespace=[set the git namespace]:' \
 		'--no-replace-objects[do not use replacement refs to replace git objects]' \
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 7283af3342..d0795ee014 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -802,7 +802,7 @@ test_expect_success 'general options' '
 	test_completion "git --no-r" "--no-replace-objects"
 '
 
-test_expect_failure 'general options plus command' '
+test_expect_success 'general options plus command' '
 	test_completion "git --version check" "" &&
 	test_completion "git --paginate check" "checkout" &&
 	test_completion "git --git-dir=foo check" "checkout" &&
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 26/51] completion: zsh: always set compset
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (24 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 25/51] completion: zsh: add excluded options Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 27/51] completion: factor out check in __gitcomp Felipe Contreras
                   ` (24 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

So we don't have to set it every time.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 7 ++-----
 1 file changed, 2 insertions(+), 5 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index d2eb221d79..41272b00e3 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -73,7 +73,6 @@ __gitcomp ()
 			esac
 			array+=("$c")
 		done
-		compset -P '*[=:]'
 		compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
 		;;
 	*)
@@ -92,7 +91,6 @@ __gitcomp ()
 			esac
 			array+=("$c")
 		done
-		compset -P '*[=:]'
 		compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
 		;;
 	esac
@@ -102,7 +100,6 @@ __gitcomp_direct ()
 {
 	emulate -L zsh
 
-	compset -P '*[=:]'
 	compadd -Q -S '' -- ${(f)1} && _ret=0
 }
 
@@ -110,7 +107,6 @@ __gitcomp_nl ()
 {
 	emulate -L zsh
 
-	compset -P '*[=:]'
 	compadd -Q -S "${4- }" -p "${2-}" -- ${(f)1} && _ret=0
 }
 
@@ -118,7 +114,6 @@ __gitcomp_file ()
 {
 	emulate -L zsh
 
-	compset -P '*[=:]'
 	compadd -f -p "${2-}" -- ${(f)1} && _ret=0
 }
 
@@ -136,6 +131,8 @@ __git_complete_command ()
 {
 	emulate -L zsh
 
+	compset -P '*[=:]'
+
 	local command="$1"
 	local completion_func="_git_${command//-/_}"
 	if (( $+functions[$completion_func] )); then
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 27/51] completion: factor out check in __gitcomp
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (25 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 26/51] completion: zsh: always set compset Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 28/51] completion: simplify equal suffix check Felipe Contreras
                   ` (23 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

This way we can reorganize the rest of the function.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 6 ++++--
 contrib/completion/git-completion.zsh  | 4 ++--
 2 files changed, 6 insertions(+), 4 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index ed126bbec4..86c335cfce 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -335,9 +335,11 @@ __gitcomp ()
 {
 	local cur_="${3-$cur}"
 
+	if [[ "$cur_" == *= ]]; then
+		return
+	fi
+
 	case "$cur_" in
-	*=)
-		;;
 	--no-*)
 		local c i=0 IFS=$' \t\n'
 		for c in $1; do
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 41272b00e3..808cf87f84 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -56,9 +56,9 @@ __gitcomp ()
 
 	local cur_="${3-$cur}"
 
+	[[ "$cur_" == *= ]] && return
+
 	case "$cur_" in
-	*=)
-		;;
 	--no-*)
 		local c IFS=$' \t\n'
 		local -a array
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 28/51] completion: simplify equal suffix check
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (26 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 27/51] completion: factor out check in __gitcomp Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 29/51] completion: refactor __gitcomp Felipe Contreras
                   ` (22 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

We know the prefix is already '--no-', there's no need to check for the
first '--'.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 2 +-
 contrib/completion/git-completion.zsh  | 2 +-
 2 files changed, 2 insertions(+), 2 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 86c335cfce..2a5e32e457 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -349,7 +349,7 @@ __gitcomp ()
 			c="$c${4-}"
 			if [[ $c == "$cur_"* ]]; then
 				case $c in
-				--*=|*.) ;;
+				*=|*.) ;;
 				*) c="$c " ;;
 				esac
 				COMPREPLY[i++]="${2-}$c"
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 808cf87f84..a8ff9c089a 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -68,7 +68,7 @@ __gitcomp ()
 			fi
 			c="$c${4-}"
 			case $c in
-			--*=|*.) ;;
+			*=|*.) ;;
 			*) c="$c " ;;
 			esac
 			array+=("$c")
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 29/51] completion: refactor __gitcomp
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (27 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 28/51] completion: simplify equal suffix check Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 30/51] completion: simplify __gitcomp Felipe Contreras
                   ` (21 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

We have two chunks of code doing exactly the same, there's no need for
that.

No functional changes.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 52 +++++++++-----------------
 contrib/completion/git-completion.zsh  | 52 ++++++++------------------
 2 files changed, 34 insertions(+), 70 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 2a5e32e457..54b2c4e589 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -339,44 +339,28 @@ __gitcomp ()
 		return
 	fi
 
-	case "$cur_" in
-	--no-*)
-		local c i=0 IFS=$' \t\n'
-		for c in $1; do
-			if [[ $c == "--" ]]; then
+	local c i=0 IFS=$' \t\n'
+	for c in $1; do
+		if [[ $c == "--" ]]; then
+			if [[ "$cur_" == --no-* ]]; then
 				continue
 			fi
-			c="$c${4-}"
-			if [[ $c == "$cur_"* ]]; then
-				case $c in
-				*=|*.) ;;
-				*) c="$c " ;;
-				esac
-				COMPREPLY[i++]="${2-}$c"
-			fi
-		done
-		;;
-	*)
-		local c i=0 IFS=$' \t\n'
-		for c in $1; do
-			if [[ $c == "--" ]]; then
-				c="--no-...${4-}"
-				if [[ $c == "$cur_"* ]]; then
-					COMPREPLY[i++]="${2-}$c "
-				fi
-				break
-			fi
-			c="$c${4-}"
+
+			c="--no-...${4-}"
 			if [[ $c == "$cur_"* ]]; then
-				case $c in
-				*=|*.) ;;
-				*) c="$c " ;;
-				esac
-				COMPREPLY[i++]="${2-}$c"
+				COMPREPLY[i++]="${2-}$c "
 			fi
-		done
-		;;
-	esac
+			break
+		fi
+		c="$c${4-}"
+		if [[ $c == "$cur_"* ]]; then
+			case $c in
+			*=|*.) ;;
+			*) c="$c " ;;
+			esac
+			COMPREPLY[i++]="${2-}$c"
+		fi
+	done
 }
 
 # Clear the variables caching builtins' options when (re-)sourcing
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index a8ff9c089a..7616f87fa2 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -58,42 +58,22 @@ __gitcomp ()
 
 	[[ "$cur_" == *= ]] && return
 
-	case "$cur_" in
-	--no-*)
-		local c IFS=$' \t\n'
-		local -a array
-		for c in ${=1}; do
-			if [[ $c == "--" ]]; then
-				continue
-			fi
-			c="$c${4-}"
-			case $c in
-			*=|*.) ;;
-			*) c="$c " ;;
-			esac
-			array+=("$c")
-		done
-		compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
-		;;
-	*)
-		local c IFS=$' \t\n'
-		local -a array
-		for c in ${=1}; do
-			if [[ $c == "--" ]]; then
-				c="--no-...${4-}"
-				array+=("$c ")
-				break
-			fi
-			c="$c${4-}"
-			case $c in
-			*=|*.) ;;
-			*) c="$c " ;;
-			esac
-			array+=("$c")
-		done
-		compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
-		;;
-	esac
+	local c IFS=$' \t\n'
+	local -a array
+	for c in ${=1}; do
+		if [[ $c == "--" ]]; then
+			[[ "$cur_" == --no-* ]] && continue
+			array+=("--no-...${4-} ")
+			break
+		fi
+		c="$c${4-}"
+		case $c in
+		*=|*.) ;;
+		*) c="$c " ;;
+		esac
+		array+=("$c")
+	done
+	compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
 }
 
 __gitcomp_direct ()
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 30/51] completion: simplify __gitcomp
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (28 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 29/51] completion: refactor __gitcomp Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 31/51] completion: bash: change suffix check in __gitcomp Felipe Contreras
                   ` (20 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

It's not possible for $cur_ to have anything more than --no- at this
point, so there's no need to add a suffix, nor check anything else.

All we are doing is checking that $cur_ matches --no, and adding a
completion if so.

This way the code reflects what we are doing.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 5 ++---
 contrib/completion/git-completion.zsh  | 2 +-
 2 files changed, 3 insertions(+), 4 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 54b2c4e589..c9315d4f9a 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -346,9 +346,8 @@ __gitcomp ()
 				continue
 			fi
 
-			c="--no-...${4-}"
-			if [[ $c == "$cur_"* ]]; then
-				COMPREPLY[i++]="${2-}$c "
+			if [[ --no == "$cur_"* ]]; then
+				COMPREPLY[i++]="--no-... "
 			fi
 			break
 		fi
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 7616f87fa2..d5f4270ee5 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -63,7 +63,7 @@ __gitcomp ()
 	for c in ${=1}; do
 		if [[ $c == "--" ]]; then
 			[[ "$cur_" == --no-* ]] && continue
-			array+=("--no-...${4-} ")
+			array+=("--no-... ")
 			break
 		fi
 		c="$c${4-}"
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 31/51] completion: bash: change suffix check in __gitcomp
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (29 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 30/51] completion: simplify __gitcomp Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 32/51] completion: improve __gitcomp suffix code Felipe Contreras
                   ` (19 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

We don't match the prefix, we shouldn't match the suffix either.

There are no functional changes since all the callers that add a suffix
add an =, and if $cur_ ended with that suffix, we would return
immediately.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index c9315d4f9a..2ff7de1274 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -351,8 +351,8 @@ __gitcomp ()
 			fi
 			break
 		fi
-		c="$c${4-}"
 		if [[ $c == "$cur_"* ]]; then
+			c="$c${4-}"
 			case $c in
 			*=|*.) ;;
 			*) c="$c " ;;
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 32/51] completion: improve __gitcomp suffix code
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (30 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 31/51] completion: bash: change suffix check in __gitcomp Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 33/51] test: completion: add missing test Felipe Contreras
                   ` (18 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

There's no point in adding a suffix after a suffix.

If a suffix is provided: we add it, if not: then the default heuristic
is used.

There's no functional change since most callers don't specify a suffix,
and the ones that do, use an =, which by default doesn't add an
additional suffix.

The only exception is __git_complete_config_variable_name, so make sure
we pass the correct suffix.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 19 +++++++++++--------
 contrib/completion/git-completion.zsh  | 18 +++++++++++-------
 2 files changed, 22 insertions(+), 15 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 2ff7de1274..d43ec03c12 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -339,7 +339,7 @@ __gitcomp ()
 		return
 	fi
 
-	local c i=0 IFS=$' \t\n'
+	local c i=0 IFS=$' \t\n' sfx
 	for c in $1; do
 		if [[ $c == "--" ]]; then
 			if [[ "$cur_" == --no-* ]]; then
@@ -352,12 +352,15 @@ __gitcomp ()
 			break
 		fi
 		if [[ $c == "$cur_"* ]]; then
-			c="$c${4-}"
-			case $c in
-			*=|*.) ;;
-			*) c="$c " ;;
-			esac
-			COMPREPLY[i++]="${2-}$c"
+			if [[ -z "${4+set}" ]]; then
+				case $c in
+				*=|*.) sfx="" ;;
+				*) sfx=" " ;;
+				esac
+			else
+				sfx="$4"
+			fi
+			COMPREPLY[i++]="${2-}$c$sfx"
 		fi
 	done
 }
@@ -2586,7 +2589,7 @@ __git_complete_config_variable_value ()
 #                 subsections) instead of the default space.
 __git_complete_config_variable_name ()
 {
-	local cur_="$cur" sfx
+	local cur_="$cur" sfx=" "
 
 	while test $# != 0; do
 		case "$1" in
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index d5f4270ee5..41aae0f454 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -58,7 +58,7 @@ __gitcomp ()
 
 	[[ "$cur_" == *= ]] && return
 
-	local c IFS=$' \t\n'
+	local c IFS=$' \t\n' sfx
 	local -a array
 	for c in ${=1}; do
 		if [[ $c == "--" ]]; then
@@ -66,12 +66,16 @@ __gitcomp ()
 			array+=("--no-... ")
 			break
 		fi
-		c="$c${4-}"
-		case $c in
-		*=|*.) ;;
-		*) c="$c " ;;
-		esac
-		array+=("$c")
+
+		if [[ -z "${4+set}" ]]; then
+			case $c in
+			*=|*.) sfx="" ;;
+			*) sfx=" " ;;
+			esac
+		else
+			sfx="$4"
+		fi
+		array+=("$c$sfx")
 	done
 	compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
 }
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 33/51] test: completion: add missing test
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (31 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 32/51] completion: improve __gitcomp suffix code Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 34/51] completion: bash: simplify config_variable_name Felipe Contreras
                   ` (17 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Once the correct suffix in __git_complete_config_variable_name() is set,
we can add the test again.

Now it should work even in bash < 4.0.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 t/t9902-completion.sh     | 7 +++++++
 t/t9904-zsh-completion.sh | 7 +++++++
 2 files changed, 14 insertions(+)

diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index 91dfb618c1..e1e9c6e365 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -2503,6 +2503,13 @@ test_expect_success 'git config - value' '
 	EOF
 '
 
+test_expect_success 'git config - direct completions' '
+	test_completion "git config branch.autoSetup" <<-\EOF
+	branch.autoSetupMerge Z
+	branch.autoSetupRebase Z
+	EOF
+'
+
 test_expect_success 'git -c - section' '
 	test_completion "git -c br" <<-\EOF
 	branch.Z
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index d0795ee014..42917833e8 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -1071,6 +1071,13 @@ test_expect_success 'git config - value' '
 	EOF
 '
 
+test_expect_success 'git config - direct completions' '
+	test_completion "git config branch.autoSetup" <<-\EOF
+	branch.autoSetupMerge Z
+	branch.autoSetupRebase Z
+	EOF
+'
+
 test_expect_success 'git -c - section' '
 	test_completion "git -c br" <<-\EOF
 	branch.Z
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 34/51] completion: bash: simplify config_variable_name
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (32 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 33/51] test: completion: add missing test Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 35/51] completion: bash: improve __gitcomp description Felipe Contreras
                   ` (16 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Now sfx is never null.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index d43ec03c12..9e15538f53 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -2611,7 +2611,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__gitcomp_direct "$(__git_heads "$pfx" "$cur_" ".")"
-		__gitcomp_nl $'autoSetupMerge\nautoSetupRebase\n' "$pfx" "$cur_" "${sfx- }"
+		__gitcomp_nl $'autoSetupMerge\nautoSetupRebase\n' "$pfx" "$cur_" "$sfx"
 		return
 		;;
 	guitool.*.*)
@@ -2645,7 +2645,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__git_compute_all_commands
-		__gitcomp_nl "$__git_all_commands" "$pfx" "$cur_" "${sfx- }"
+		__gitcomp_nl "$__git_all_commands" "$pfx" "$cur_" "$sfx"
 		return
 		;;
 	remote.*.*)
@@ -2661,7 +2661,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__gitcomp_nl "$(__git_remotes)" "$pfx" "$cur_" "."
-		__gitcomp_nl "pushDefault" "$pfx" "$cur_" "${sfx- }"
+		__gitcomp_nl "pushDefault" "$pfx" "$cur_" "$sfx"
 		return
 		;;
 	url.*.*)
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 35/51] completion: bash: improve __gitcomp description
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (33 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 34/51] completion: bash: simplify config_variable_name Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 36/51] completion: add __gitcomp_opts Felipe Contreras
                   ` (15 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

It does a lot more than what is stated now.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 3 +--
 1 file changed, 1 insertion(+), 2 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 9e15538f53..6610054e0e 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -324,8 +324,7 @@ __gitcompadd ()
 	done
 }
 
-# Generates completion reply, appending a space to possible completion words,
-# if necessary.
+# Creates completion replies, reorganizing options and adding suffixes as needed.
 # It accepts 1 to 4 arguments:
 # 1: List of possible completion words.
 # 2: A prefix to be added to each possible completion word (optional).
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 36/51] completion: add __gitcomp_opts
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (34 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 35/51] completion: bash: improve __gitcomp description Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 37/51] completion: bash: cleanup __gitcomp* invocations Felipe Contreras
                   ` (14 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Create a new simplified version of __gitcomp for most callers, and
__gitcomp_opts for the ones that need reorganizing all the options.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 94 +++++++++++++++-----------
 contrib/completion/git-completion.zsh  |  8 +++
 t/t9902-completion.sh                  | 58 ++++++++--------
 t/t9904-zsh-completion.sh              | 54 +++++++--------
 4 files changed, 117 insertions(+), 97 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 6610054e0e..2cedbd6cc8 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -324,13 +324,25 @@ __gitcompadd ()
 	done
 }
 
-# Creates completion replies, reorganizing options and adding suffixes as needed.
+# Creates completion replies.
 # It accepts 1 to 4 arguments:
 # 1: List of possible completion words.
 # 2: A prefix to be added to each possible completion word (optional).
 # 3: Generate possible completion matches for this word (optional).
 # 4: A suffix to be appended to each possible completion word (optional).
 __gitcomp ()
+{
+	local IFS=$' \t\n'
+	__gitcompadd "$1" "${2-}" "${3-$cur}" "${4- }"
+}
+
+# Creates completion replies, reorganizing options and adding suffixes as needed.
+# It accepts 1 to 4 arguments:
+# 1: List of possible completion words.
+# 2: A prefix to be added to each possible completion word (optional).
+# 3: Generate possible completion matches for this word (optional).
+# 4: A suffix to be appended to each possible completion word (optional).
+__gitcomp_opts ()
 {
 	local cur_="${3-$cur}"
 
@@ -374,7 +386,7 @@ fi
 
 # This function is equivalent to
 #
-#    __gitcomp "$(git xxx --git-completion-helper) ..."
+#    __gitcomp_opts "$(git xxx --git-completion-helper) ..."
 #
 # except that the output is cached. Accept 1-3 arguments:
 # 1: the git command to execute, this is also the cache key
@@ -409,7 +421,7 @@ __gitcomp_builtin ()
 		eval "$var=\"$options\""
 	fi
 
-	__gitcomp "$options"
+	__gitcomp_opts "$options"
 }
 
 # Generates completion reply from newline-separated possible completion words
@@ -1046,7 +1058,7 @@ __git_complete_strategy ()
 		return 0
 		;;
 	-X)
-		__gitcomp "$__git_merge_strategy_options"
+		__gitcomp_opts "$__git_merge_strategy_options"
 		return 0
 		;;
 	esac
@@ -1056,7 +1068,7 @@ __git_complete_strategy ()
 		return 0
 		;;
 	--strategy-option=*)
-		__gitcomp "$__git_merge_strategy_options" "" "${cur##--strategy-option=}"
+		__gitcomp_opts "$__git_merge_strategy_options" "" "${cur##--strategy-option=}"
 		return 0
 		;;
 	esac
@@ -1298,7 +1310,7 @@ _git_am ()
 {
 	__git_find_repo_path
 	if [ -d "$__git_repo_path"/rebase-apply ]; then
-		__gitcomp "$__git_am_inprogress_options"
+		__gitcomp_opts "$__git_am_inprogress_options"
 		return
 	fi
 	case "$cur" in
@@ -1558,7 +1570,7 @@ _git_cherry_pick ()
 {
 	__git_find_repo_path
 	if [ -f "$__git_repo_path"/CHERRY_PICK_HEAD ]; then
-		__gitcomp "$__git_cherry_pick_inprogress_options"
+		__gitcomp_opts "$__git_cherry_pick_inprogress_options"
 		return
 	fi
 
@@ -1717,7 +1729,7 @@ _git_diff ()
 		return
 		;;
 	--*)
-		__gitcomp "$__git_diff_difftool_options"
+		__gitcomp_opts "$__git_diff_difftool_options"
 		return
 		;;
 	esac
@@ -2011,7 +2023,7 @@ _git_log ()
 		return
 		;;
 	--*)
-		__gitcomp "
+		__gitcomp_opts "
 			$__git_log_common_options
 			$__git_log_shortlog_options
 			$__git_log_gitk_options
@@ -2074,7 +2086,7 @@ _git_mergetool ()
 		return
 		;;
 	--*)
-		__gitcomp "--tool= --prompt --no-prompt --gui --no-gui"
+		__gitcomp_opts "--tool= --prompt --no-prompt --gui --no-gui"
 		return
 		;;
 	esac
@@ -2222,7 +2234,7 @@ _git_range_diff ()
 {
 	case "$cur" in
 	--*)
-		__gitcomp "
+		__gitcomp_opts "
 			--creation-factor= --no-dual-color
 			$__git_diff_common_options
 		"
@@ -2239,11 +2251,11 @@ _git_rebase ()
 {
 	__git_find_repo_path
 	if [ -f "$__git_repo_path"/rebase-merge/interactive ]; then
-		__gitcomp "$__git_rebase_interactive_inprogress_options"
+		__gitcomp_opts "$__git_rebase_interactive_inprogress_options"
 		return
 	elif [ -d "$__git_repo_path"/rebase-apply ] || \
 	     [ -d "$__git_repo_path"/rebase-merge ]; then
-		__gitcomp "$__git_rebase_inprogress_options"
+		__gitcomp_opts "$__git_rebase_inprogress_options"
 		return
 	fi
 	__git_complete_strategy && return
@@ -2857,7 +2869,7 @@ _git_revert ()
 {
 	__git_find_repo_path
 	if [ -f "$__git_repo_path"/REVERT_HEAD ]; then
-		__gitcomp "$__git_revert_inprogress_options"
+		__gitcomp_opts "$__git_revert_inprogress_options"
 		return
 	fi
 	__git_complete_strategy && return
@@ -2889,7 +2901,7 @@ _git_shortlog ()
 
 	case "$cur" in
 	--*)
-		__gitcomp "
+		__gitcomp_opts "
 			$__git_log_common_options
 			$__git_log_shortlog_options
 			--numbered --summary --email
@@ -2927,7 +2939,7 @@ _git_show ()
 		return
 		;;
 	--*)
-		__gitcomp "--pretty= --format= --abbrev-commit --no-abbrev-commit
+		__gitcomp_opts "--pretty= --format= --abbrev-commit --no-abbrev-commit
 			--oneline --show-signature
 			--expand-tabs --expand-tabs= --no-expand-tabs
 			$__git_diff_common_options
@@ -3053,7 +3065,7 @@ _git_submodule ()
 	if [ -z "$subcommand" ]; then
 		case "$cur" in
 		--*)
-			__gitcomp "--quiet"
+			__gitcomp_opts "--quiet"
 			;;
 		*)
 			__gitcomp "$subcommands"
@@ -3064,29 +3076,29 @@ _git_submodule ()
 
 	case "$subcommand,$cur" in
 	add,--*)
-		__gitcomp "--branch --force --name --reference --depth"
+		__gitcomp_opts "--branch --force --name --reference --depth"
 		;;
 	status,--*)
-		__gitcomp "--cached --recursive"
+		__gitcomp_opts "--cached --recursive"
 		;;
 	deinit,--*)
-		__gitcomp "--force --all"
+		__gitcomp_opts "--force --all"
 		;;
 	update,--*)
-		__gitcomp "
+		__gitcomp_opts "
 			--init --remote --no-fetch
 			--recommend-shallow --no-recommend-shallow
 			--force --rebase --merge --reference --depth --recursive --jobs
 		"
 		;;
 	set-branch,--*)
-		__gitcomp "--default --branch"
+		__gitcomp_opts "--default --branch"
 		;;
 	summary,--*)
-		__gitcomp "--cached --files --summary-limit"
+		__gitcomp_opts "--cached --files --summary-limit"
 		;;
 	foreach,--*|sync,--*)
-		__gitcomp "--recursive"
+		__gitcomp_opts "--recursive"
 		;;
 	*)
 		;;
@@ -3127,64 +3139,64 @@ _git_svn ()
 
 		case "$subcommand,$cur" in
 		fetch,--*)
-			__gitcomp "--revision= --fetch-all $fc_opts"
+			__gitcomp_opts "--revision= --fetch-all $fc_opts"
 			;;
 		clone,--*)
-			__gitcomp "--revision= $fc_opts $init_opts"
+			__gitcomp_opts "--revision= $fc_opts $init_opts"
 			;;
 		init,--*)
-			__gitcomp "$init_opts"
+			__gitcomp_opts "$init_opts"
 			;;
 		dcommit,--*)
-			__gitcomp "
+			__gitcomp_opts "
 				--merge --strategy= --verbose --dry-run
 				--fetch-all --no-rebase --commit-url
 				--revision --interactive $cmt_opts $fc_opts
 				"
 			;;
 		set-tree,--*)
-			__gitcomp "--stdin $cmt_opts $fc_opts"
+			__gitcomp_opts "--stdin $cmt_opts $fc_opts"
 			;;
 		create-ignore,--*|propget,--*|proplist,--*|show-ignore,--*|\
 		show-externals,--*|mkdirs,--*)
-			__gitcomp "--revision="
+			__gitcomp_opts "--revision="
 			;;
 		log,--*)
-			__gitcomp "
+			__gitcomp_opts "
 				--limit= --revision= --verbose --incremental
 				--oneline --show-commit --non-recursive
 				--authors-file= --color
 				"
 			;;
 		rebase,--*)
-			__gitcomp "
+			__gitcomp_opts "
 				--merge --verbose --strategy= --local
 				--fetch-all --dry-run $fc_opts
 				"
 			;;
 		commit-diff,--*)
-			__gitcomp "--message= --file= --revision= $cmt_opts"
+			__gitcomp_opts "--message= --file= --revision= $cmt_opts"
 			;;
 		info,--*)
-			__gitcomp "--url"
+			__gitcomp_opts "--url"
 			;;
 		branch,--*)
-			__gitcomp "--dry-run --message --tag"
+			__gitcomp_opts "--dry-run --message --tag"
 			;;
 		tag,--*)
-			__gitcomp "--dry-run --message"
+			__gitcomp_opts "--dry-run --message"
 			;;
 		blame,--*)
-			__gitcomp "--git-format"
+			__gitcomp_opts "--git-format"
 			;;
 		migrate,--*)
-			__gitcomp "
+			__gitcomp_opts "
 				--config-dir= --ignore-paths= --minimize
 				--no-auth-cache --username=
 				"
 			;;
 		reset,--*)
-			__gitcomp "--revision= --parent"
+			__gitcomp_opts "--revision= --parent"
 			;;
 		*)
 			;;
@@ -3424,7 +3436,7 @@ __git_main ()
 		esac
 		case "$cur" in
 		--*)
-			__gitcomp "
+			__gitcomp_opts "
 			--paginate
 			--no-pager
 			--git-dir=
@@ -3481,7 +3493,7 @@ __gitk_main ()
 	fi
 	case "$cur" in
 	--*)
-		__gitcomp "
+		__gitcomp_opts "
 			$__git_log_common_options
 			$__git_log_gitk_options
 			$merge
diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 41aae0f454..2ad24f1510 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -54,6 +54,14 @@ __gitcomp ()
 {
 	emulate -L zsh
 
+	local IFS=$' \t\n'
+	compadd -Q -S "${4- }" -p "${2-}" -- ${=1} && _ret=0
+}
+
+__gitcomp_opts ()
+{
+	emulate -L zsh
+
 	local cur_="${3-$cur}"
 
 	[[ "$cur_" == *= ]] && return
diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index e1e9c6e365..eb8e173e6b 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -98,17 +98,17 @@ test_completion ()
 	test_cmp expected out_sorted
 }
 
-# Test __gitcomp.
+# Test __gitcomp_opts.
 # The first argument is the typed text so far (cur); the rest are
-# passed to __gitcomp.  Expected output comes is read from the
+# passed to __gitcomp_opts.  Expected output comes is read from the
 # standard input, like test_completion().
-test_gitcomp ()
+test_gitcomp_opts ()
 {
 	local -a COMPREPLY &&
 	sed -e 's/Z$//' >expected &&
 	local cur="$1" &&
 	shift &&
-	__gitcomp "$@" &&
+	__gitcomp_opts "$@" &&
 	print_comp &&
 	test_cmp expected out
 }
@@ -463,8 +463,8 @@ test_expect_success '__gitcomp_direct - puts everything into COMPREPLY as-is' '
 	test_cmp expected out
 '
 
-test_expect_success '__gitcomp - trailing space - options' '
-	test_gitcomp "--re" "--dry-run --reuse-message= --reedit-message=
+test_expect_success '__gitcomp_opts - trailing space - options' '
+	test_gitcomp_opts "--re" "--dry-run --reuse-message= --reedit-message=
 		--reset-author" <<-EOF
 	--reuse-message=Z
 	--reedit-message=Z
@@ -472,8 +472,8 @@ test_expect_success '__gitcomp - trailing space - options' '
 	EOF
 '
 
-test_expect_success '__gitcomp - trailing space - config keys' '
-	test_gitcomp "br" "branch. branch.autosetupmerge
+test_expect_success '__gitcomp_opts - trailing space - config keys' '
+	test_gitcomp_opts "br" "branch. branch.autosetupmerge
 		branch.autosetuprebase browser." <<-\EOF
 	branch.Z
 	branch.autosetupmerge Z
@@ -482,32 +482,32 @@ test_expect_success '__gitcomp - trailing space - config keys' '
 	EOF
 '
 
-test_expect_success '__gitcomp - option parameter' '
-	test_gitcomp "--strategy=re" "octopus ours recursive resolve subtree" \
+test_expect_success '__gitcomp_opts - option parameter' '
+	test_gitcomp_opts "--strategy=re" "octopus ours recursive resolve subtree" \
 		"" "re" <<-\EOF
 	recursive Z
 	resolve Z
 	EOF
 '
 
-test_expect_success '__gitcomp - prefix' '
-	test_gitcomp "branch.maint.me" "remote merge mergeoptions rebase" \
+test_expect_success '__gitcomp_opts - prefix' '
+	test_gitcomp_opts "branch.maint.me" "remote merge mergeoptions rebase" \
 		"branch.maint." "me" <<-\EOF
 	branch.maint.merge Z
 	branch.maint.mergeoptions Z
 	EOF
 '
 
-test_expect_success '__gitcomp - suffix' '
-	test_gitcomp "branch.ma" "master maint next seen" "branch." \
+test_expect_success '__gitcomp_opts - suffix' '
+	test_gitcomp_opts "branch.ma" "master maint next seen" "branch." \
 		"ma" "." <<-\EOF
 	branch.master.Z
 	branch.maint.Z
 	EOF
 '
 
-test_expect_success '__gitcomp - ignore optional negative options' '
-	test_gitcomp "--" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - ignore optional negative options' '
+	test_gitcomp_opts "--" "--abc --def --no-one -- --no-two" <<-\EOF
 	--abc Z
 	--def Z
 	--no-one Z
@@ -515,44 +515,44 @@ test_expect_success '__gitcomp - ignore optional negative options' '
 	EOF
 '
 
-test_expect_success '__gitcomp - ignore/narrow optional negative options' '
-	test_gitcomp "--a" "--abc --abcdef --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - ignore/narrow optional negative options' '
+	test_gitcomp_opts "--a" "--abc --abcdef --no-one -- --no-two" <<-\EOF
 	--abc Z
 	--abcdef Z
 	EOF
 '
 
-test_expect_success '__gitcomp - ignore/narrow optional negative options' '
-	test_gitcomp "--n" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - ignore/narrow optional negative options' '
+	test_gitcomp_opts "--n" "--abc --def --no-one -- --no-two" <<-\EOF
 	--no-one Z
 	--no-... Z
 	EOF
 '
 
-test_expect_success '__gitcomp - expand all negative options' '
-	test_gitcomp "--no-" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - expand all negative options' '
+	test_gitcomp_opts "--no-" "--abc --def --no-one -- --no-two" <<-\EOF
 	--no-one Z
 	--no-two Z
 	EOF
 '
 
-test_expect_success '__gitcomp - expand/narrow all negative options' '
-	test_gitcomp "--no-o" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - expand/narrow all negative options' '
+	test_gitcomp_opts "--no-o" "--abc --def --no-one -- --no-two" <<-\EOF
 	--no-one Z
 	EOF
 '
 
-test_expect_success '__gitcomp - equal skip' '
-	test_gitcomp "--option=" "--option=" <<-\EOF &&
+test_expect_success '__gitcomp_opts - equal skip' '
+	test_gitcomp_opts "--option=" "--option=" <<-\EOF &&
 
 	EOF
-	test_gitcomp "option=" "option=" <<-\EOF
+	test_gitcomp_opts "option=" "option=" <<-\EOF
 
 	EOF
 '
 
-test_expect_success '__gitcomp - doesnt fail because of invalid variable name' '
-	run_func __gitcomp "$invalid_variable_name"
+test_expect_success '__gitcomp_opts - doesnt fail because of invalid variable name' '
+	run_func __gitcomp_opts "$invalid_variable_name"
 '
 
 read -r -d "" refs <<-\EOF
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 42917833e8..894f3287f4 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -37,16 +37,16 @@ test_completion ()
 	test_cmp expected out_sorted
 }
 
-# Test __gitcomp.
+# Test __gitcomp_opts.
 # The first argument is the typed text so far (cur); the rest are
-# passed to __gitcomp.  Expected output comes is read from the
+# passed to __gitcomp_opts.  Expected output comes is read from the
 # standard input, like test_completion().
-test_gitcomp ()
+test_gitcomp_opts ()
 {
 	sed -e 's/Z$//' >expected &&
 	local cur="$1" &&
 	shift &&
-	run_completion "git func __gitcomp $(printf "%q " "$@") $cur" &&
+	run_completion "git func __gitcomp_opts $(printf "%q " "$@") $cur" &&
 	test_cmp expected out
 }
 
@@ -78,8 +78,8 @@ test_expect_success 'setup for __git_find_repo_path/__gitdir tests' '
 	git init -b main otherrepo
 '
 
-test_expect_success '__gitcomp - trailing space - options' '
-	test_gitcomp "--re" "--dry-run --reuse-message= --reedit-message=
+test_expect_success '__gitcomp_opts - trailing space - options' '
+	test_gitcomp_opts "--re" "--dry-run --reuse-message= --reedit-message=
 		--reset-author" <<-EOF
 	--reuse-message=Z
 	--reedit-message=Z
@@ -87,8 +87,8 @@ test_expect_success '__gitcomp - trailing space - options' '
 	EOF
 '
 
-test_expect_success '__gitcomp - trailing space - config keys' '
-	test_gitcomp "br" "branch. branch.autosetupmerge
+test_expect_success '__gitcomp_opts - trailing space - config keys' '
+	test_gitcomp_opts "br" "branch. branch.autosetupmerge
 		branch.autosetuprebase browser." <<-\EOF
 	branch.Z
 	branch.autosetupmerge Z
@@ -97,32 +97,32 @@ test_expect_success '__gitcomp - trailing space - config keys' '
 	EOF
 '
 
-test_expect_success '__gitcomp - option parameter' '
-	test_gitcomp "--strategy=re" "octopus ours recursive resolve subtree" \
+test_expect_success '__gitcomp_opts - option parameter' '
+	test_gitcomp_opts "--strategy=re" "octopus ours recursive resolve subtree" \
 		"" "re" <<-\EOF
 	recursive Z
 	resolve Z
 	EOF
 '
 
-test_expect_failure '__gitcomp - prefix' '
-	test_gitcomp "branch.maint.me" "remote merge mergeoptions rebase" \
+test_expect_failure '__gitcomp_opts - prefix' '
+	test_gitcomp_opts "branch.maint.me" "remote merge mergeoptions rebase" \
 		"branch.maint." "me" <<-\EOF
 	branch.maint.merge Z
 	branch.maint.mergeoptions Z
 	EOF
 '
 
-test_expect_failure '__gitcomp - suffix' '
-	test_gitcomp "branch.ma" "master maint next seen" "branch." \
+test_expect_failure '__gitcomp_opts - suffix' '
+	test_gitcomp_opts "branch.ma" "master maint next seen" "branch." \
 		"ma" "." <<-\EOF
 	branch.master.Z
 	branch.maint.Z
 	EOF
 '
 
-test_expect_success '__gitcomp - ignore optional negative options' '
-	test_gitcomp "--" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - ignore optional negative options' '
+	test_gitcomp_opts "--" "--abc --def --no-one -- --no-two" <<-\EOF
 	--abc Z
 	--def Z
 	--no-one Z
@@ -130,38 +130,38 @@ test_expect_success '__gitcomp - ignore optional negative options' '
 	EOF
 '
 
-test_expect_success '__gitcomp - ignore/narrow optional negative options' '
-	test_gitcomp "--a" "--abc --abcdef --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - ignore/narrow optional negative options' '
+	test_gitcomp_opts "--a" "--abc --abcdef --no-one -- --no-two" <<-\EOF
 	--abc Z
 	--abcdef Z
 	EOF
 '
 
-test_expect_success '__gitcomp - ignore/narrow optional negative options' '
-	test_gitcomp "--n" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - ignore/narrow optional negative options' '
+	test_gitcomp_opts "--n" "--abc --def --no-one -- --no-two" <<-\EOF
 	--no-one Z
 	--no-... Z
 	EOF
 '
 
-test_expect_success '__gitcomp - expand all negative options' '
-	test_gitcomp "--no-" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - expand all negative options' '
+	test_gitcomp_opts "--no-" "--abc --def --no-one -- --no-two" <<-\EOF
 	--no-one Z
 	--no-two Z
 	EOF
 '
 
-test_expect_success '__gitcomp - expand/narrow all negative options' '
-	test_gitcomp "--no-o" "--abc --def --no-one -- --no-two" <<-\EOF
+test_expect_success '__gitcomp_opts - expand/narrow all negative options' '
+	test_gitcomp_opts "--no-o" "--abc --def --no-one -- --no-two" <<-\EOF
 	--no-one Z
 	EOF
 '
 
-test_expect_success '__gitcomp - equal skip' '
-	test_gitcomp "--option=" "--option=" <<-\EOF &&
+test_expect_success '__gitcomp_opts - equal skip' '
+	test_gitcomp_opts "--option=" "--option=" <<-\EOF &&
 
 	EOF
-	test_gitcomp "option=" "option=" <<-\EOF
+	test_gitcomp_opts "option=" "option=" <<-\EOF
 
 	EOF
 '
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 37/51] completion: bash: cleanup __gitcomp* invocations
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (35 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 36/51] completion: add __gitcomp_opts Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 38/51] completion: bash: shuffle __gitcomp functions Felipe Contreras
                   ` (13 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Some __gitcomp calls should be __gitcomp_nl, and vice versa.

No functional changes.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 22 +++++++++-------------
 1 file changed, 9 insertions(+), 13 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 2cedbd6cc8..499ccd3a93 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -1374,7 +1374,7 @@ _git_archive ()
 {
 	case "$cur" in
 	--format=*)
-		__gitcomp "$(git archive --list)" "" "${cur##--format=}"
+		__gitcomp_nl "$(git archive --list)" "" "${cur##--format=}"
 		return
 		;;
 	--remote=*)
@@ -1788,9 +1788,7 @@ _git_format_patch ()
 {
 	case "$cur" in
 	--thread=*)
-		__gitcomp "
-			deep shallow
-			" "" "${cur##--thread=}"
+		__gitcomp "deep shallow" "" "${cur##--thread=}"
 		return
 		;;
 	--base=*|--interdiff=*|--range-diff=*)
@@ -2296,7 +2294,7 @@ _git_send_email ()
 {
 	case "$prev" in
 	--to|--cc|--bcc|--from)
-		__gitcomp "$(__git send-email --dump-aliases)"
+		__gitcomp_nl "$(__git send-email --dump-aliases)"
 		return
 		;;
 	esac
@@ -2320,9 +2318,7 @@ _git_send_email ()
 		return
 		;;
 	--thread=*)
-		__gitcomp "
-			deep shallow
-			" "" "${cur##--thread=}"
+		__gitcomp "deep shallow" "" "${cur##--thread=}"
 		return
 		;;
 	--to=*|--cc=*|--bcc=*|--from=*)
@@ -2622,7 +2618,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__gitcomp_direct "$(__git_heads "$pfx" "$cur_" ".")"
-		__gitcomp_nl $'autoSetupMerge\nautoSetupRebase\n' "$pfx" "$cur_" "$sfx"
+		__gitcomp "autoSetupMerge autoSetupRebase" "$pfx" "$cur_" "$sfx"
 		return
 		;;
 	guitool.*.*)
@@ -2672,7 +2668,7 @@ __git_complete_config_variable_name ()
 		local pfx="${cur_%.*}."
 		cur_="${cur_#*.}"
 		__gitcomp_nl "$(__git_remotes)" "$pfx" "$cur_" "."
-		__gitcomp_nl "pushDefault" "$pfx" "$cur_" "$sfx"
+		__gitcomp "pushDefault" "$pfx" "$cur_" "$sfx"
 		return
 		;;
 	url.*.*)
@@ -2687,7 +2683,7 @@ __git_complete_config_variable_name ()
 		;;
 	*)
 		__git_compute_config_sections
-		__gitcomp "$__git_config_sections" "" "$cur_" "."
+		__gitcomp_nl "$__git_config_sections" "" "$cur_" "."
 		;;
 	esac
 }
@@ -2781,7 +2777,7 @@ _git_remote ()
 		__gitcomp_builtin remote_update
 		;;
 	update,*)
-		__gitcomp "$(__git_remotes) $(__git_get_config_variables "remotes")"
+		__gitcomp_nl "$(__git_remotes) $(__git_get_config_variables "remotes")"
 		;;
 	set-url,--*)
 		__gitcomp_builtin remote_set-url
@@ -3464,7 +3460,7 @@ __git_main ()
 				then
 					list_cmds=builtins,$list_cmds
 				fi
-				__gitcomp "$(__git --list-cmds=$list_cmds)"
+				__gitcomp_nl "$(__git --list-cmds=$list_cmds)"
 			fi
 			;;
 		esac
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 38/51] completion: bash: shuffle __gitcomp functions
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (36 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 37/51] completion: bash: cleanup __gitcomp* invocations Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 39/51] completion: zsh: simplify __gitcomp_direct Felipe Contreras
                   ` (12 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

They are the ones that actually do the completion, put them at the top.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 270 +++++++++++++------------
 1 file changed, 139 insertions(+), 131 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 499ccd3a93..1fb99265e4 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -59,6 +59,145 @@
 #     When set to "1" suggest all options, including options which are
 #     typically hidden (e.g. '--allow-empty' for 'git commit').
 
+# The following functions are meant to modify COMPREPLY, which should not be
+# modified directly.  The purpose is to localize the modifications so it's
+# easier to emulate it in Zsh. Every time a new __gitcomp* function is added,
+# the corresponding function should be added to Zsh.
+
+__gitcompadd ()
+{
+	local x i=${#COMPREPLY[@]}
+	for x in $1; do
+		if [[ "$x" == "$3"* ]]; then
+			COMPREPLY[i++]="$2$x$4"
+		fi
+	done
+}
+
+# Creates completion replies.
+# It accepts 1 to 4 arguments:
+# 1: List of possible completion words.
+# 2: A prefix to be added to each possible completion word (optional).
+# 3: Generate possible completion matches for this word (optional).
+# 4: A suffix to be appended to each possible completion word (optional).
+__gitcomp ()
+{
+	local IFS=$' \t\n'
+	__gitcompadd "$1" "${2-}" "${3-$cur}" "${4- }"
+}
+
+# Generates completion reply from newline-separated possible completion words
+# by appending a space to all of them. The result is appended to COMPREPLY.
+# It accepts 1 to 4 arguments:
+# 1: List of possible completion words, separated by a single newline.
+# 2: A prefix to be added to each possible completion word (optional).
+# 3: Generate possible completion matches for this word (optional).
+# 4: A suffix to be appended to each possible completion word instead of
+#    the default space (optional).  If specified but empty, nothing is
+#    appended.
+__gitcomp_nl ()
+{
+	local IFS=$'\n'
+	__gitcompadd "$1" "${2-}" "${3-$cur}" "${4- }"
+}
+
+# Appends prefiltered words to COMPREPLY without any additional processing.
+# Callers must take care of providing only words that match the current word
+# to be completed and adding any prefix and/or suffix (trailing space!), if
+# necessary.
+# 1: List of newline-separated matching completion words, complete with
+#    prefix and suffix.
+__gitcomp_direct ()
+{
+	local IFS=$'\n'
+
+	COMPREPLY+=($1)
+}
+
+# Generates completion reply with compgen from newline-separated possible
+# completion filenames.
+# It accepts 1 to 3 arguments:
+# 1: List of possible completion filenames, separated by a single newline.
+# 2: A directory prefix to be added to each possible completion filename
+#    (optional).
+# 3: Generate possible completion matches for this word (optional).
+__gitcomp_file ()
+{
+	local IFS=$'\n'
+
+	# XXX does not work when the directory prefix contains a tilde,
+	# since tilde expansion is not applied.
+	# This means that COMPREPLY will be empty and Bash default
+	# completion will be used.
+	__gitcompadd "$1" "${2-}" "${3-$cur}" ""
+
+	# use a hack to enable file mode in bash < 4
+	compopt -o filenames +o nospace 2>/dev/null ||
+	compgen -f /non-existing-dir/ >/dev/null ||
+	true
+}
+
+# Fills the COMPREPLY array with prefiltered paths without any additional
+# processing.
+# Callers must take care of providing only paths that match the current path
+# to be completed and adding any prefix path components, if necessary.
+# 1: List of newline-separated matching paths, complete with all prefix
+#    path components.
+__gitcomp_file_direct ()
+{
+	local IFS=$'\n'
+
+	COMPREPLY+=($1)
+
+	# use a hack to enable file mode in bash < 4
+	compopt -o filenames +o nospace 2>/dev/null ||
+	compgen -f /non-existing-dir/ >/dev/null ||
+	true
+}
+
+# Creates completion replies, reorganizing options and adding suffixes as needed.
+# It accepts 1 to 4 arguments:
+# 1: List of possible completion words.
+# 2: A prefix to be added to each possible completion word (optional).
+# 3: Generate possible completion matches for this word (optional).
+# 4: A suffix to be appended to each possible completion word (optional).
+__gitcomp_opts ()
+{
+	local cur_="${3-$cur}"
+
+	if [[ "$cur_" == *= ]]; then
+		return
+	fi
+
+	local c i=0 IFS=$' \t\n' sfx
+	for c in $1; do
+		if [[ $c == "--" ]]; then
+			if [[ "$cur_" == --no-* ]]; then
+				continue
+			fi
+
+			if [[ --no == "$cur_"* ]]; then
+				COMPREPLY[i++]="--no-... "
+			fi
+			break
+		fi
+		if [[ $c == "$cur_"* ]]; then
+			if [[ -z "${4+set}" ]]; then
+				case $c in
+				*=|*.) sfx="" ;;
+				*) sfx=" " ;;
+				esac
+			else
+				sfx="$4"
+			fi
+			COMPREPLY[i++]="${2-}$c$sfx"
+		fi
+	done
+}
+
+# __gitcomp functions end here
+# ==============================================================================
+
 # Discovers the path to the git repository taking any '--git-dir=<path>' and
 # '-C <path>' options into account and stores it in the $__git_repo_path
 # variable.
@@ -301,81 +440,6 @@ _get_comp_words_by_ref ()
 }
 fi
 
-# Appends prefiltered words to COMPREPLY without any additional processing.
-# Callers must take care of providing only words that match the current word
-# to be completed and adding any prefix and/or suffix (trailing space!), if
-# necessary.
-# 1: List of newline-separated matching completion words, complete with
-#    prefix and suffix.
-__gitcomp_direct ()
-{
-	local IFS=$'\n'
-
-	COMPREPLY+=($1)
-}
-
-__gitcompadd ()
-{
-	local x i=${#COMPREPLY[@]}
-	for x in $1; do
-		if [[ "$x" == "$3"* ]]; then
-			COMPREPLY[i++]="$2$x$4"
-		fi
-	done
-}
-
-# Creates completion replies.
-# It accepts 1 to 4 arguments:
-# 1: List of possible completion words.
-# 2: A prefix to be added to each possible completion word (optional).
-# 3: Generate possible completion matches for this word (optional).
-# 4: A suffix to be appended to each possible completion word (optional).
-__gitcomp ()
-{
-	local IFS=$' \t\n'
-	__gitcompadd "$1" "${2-}" "${3-$cur}" "${4- }"
-}
-
-# Creates completion replies, reorganizing options and adding suffixes as needed.
-# It accepts 1 to 4 arguments:
-# 1: List of possible completion words.
-# 2: A prefix to be added to each possible completion word (optional).
-# 3: Generate possible completion matches for this word (optional).
-# 4: A suffix to be appended to each possible completion word (optional).
-__gitcomp_opts ()
-{
-	local cur_="${3-$cur}"
-
-	if [[ "$cur_" == *= ]]; then
-		return
-	fi
-
-	local c i=0 IFS=$' \t\n' sfx
-	for c in $1; do
-		if [[ $c == "--" ]]; then
-			if [[ "$cur_" == --no-* ]]; then
-				continue
-			fi
-
-			if [[ --no == "$cur_"* ]]; then
-				COMPREPLY[i++]="--no-... "
-			fi
-			break
-		fi
-		if [[ $c == "$cur_"* ]]; then
-			if [[ -z "${4+set}" ]]; then
-				case $c in
-				*=|*.) sfx="" ;;
-				*) sfx=" " ;;
-				esac
-			else
-				sfx="$4"
-			fi
-			COMPREPLY[i++]="${2-}$c$sfx"
-		fi
-	done
-}
-
 # Clear the variables caching builtins' options when (re-)sourcing
 # the completion script.
 if [[ -n ${ZSH_VERSION-} ]]; then
@@ -424,62 +488,6 @@ __gitcomp_builtin ()
 	__gitcomp_opts "$options"
 }
 
-# Generates completion reply from newline-separated possible completion words
-# by appending a space to all of them. The result is appended to COMPREPLY.
-# It accepts 1 to 4 arguments:
-# 1: List of possible completion words, separated by a single newline.
-# 2: A prefix to be added to each possible completion word (optional).
-# 3: Generate possible completion matches for this word (optional).
-# 4: A suffix to be appended to each possible completion word instead of
-#    the default space (optional).  If specified but empty, nothing is
-#    appended.
-__gitcomp_nl ()
-{
-	local IFS=$'\n'
-	__gitcompadd "$1" "${2-}" "${3-$cur}" "${4- }"
-}
-
-# Fills the COMPREPLY array with prefiltered paths without any additional
-# processing.
-# Callers must take care of providing only paths that match the current path
-# to be completed and adding any prefix path components, if necessary.
-# 1: List of newline-separated matching paths, complete with all prefix
-#    path components.
-__gitcomp_file_direct ()
-{
-	local IFS=$'\n'
-
-	COMPREPLY+=($1)
-
-	# use a hack to enable file mode in bash < 4
-	compopt -o filenames +o nospace 2>/dev/null ||
-	compgen -f /non-existing-dir/ >/dev/null ||
-	true
-}
-
-# Generates completion reply with compgen from newline-separated possible
-# completion filenames.
-# It accepts 1 to 3 arguments:
-# 1: List of possible completion filenames, separated by a single newline.
-# 2: A directory prefix to be added to each possible completion filename
-#    (optional).
-# 3: Generate possible completion matches for this word (optional).
-__gitcomp_file ()
-{
-	local IFS=$'\n'
-
-	# XXX does not work when the directory prefix contains a tilde,
-	# since tilde expansion is not applied.
-	# This means that COMPREPLY will be empty and Bash default
-	# completion will be used.
-	__gitcompadd "$1" "${2-}" "${3-$cur}" ""
-
-	# use a hack to enable file mode in bash < 4
-	compopt -o filenames +o nospace 2>/dev/null ||
-	compgen -f /non-existing-dir/ >/dev/null ||
-	true
-}
-
 # Execute 'git ls-files', unless the --committable option is specified, in
 # which case it runs 'git diff-index' to find out the files that can be
 # committed.  It return paths relative to the directory specified in the first
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 39/51] completion: zsh: simplify __gitcomp_direct
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (37 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 38/51] completion: bash: shuffle __gitcomp functions Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 40/51] completion: zsh: shuffle __gitcomp* functions Felipe Contreras
                   ` (11 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Not much different from __gitcomp_nl.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 4 +---
 1 file changed, 1 insertion(+), 3 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 2ad24f1510..3619c93ea9 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -90,9 +90,7 @@ __gitcomp_opts ()
 
 __gitcomp_direct ()
 {
-	emulate -L zsh
-
-	compadd -Q -S '' -- ${(f)1} && _ret=0
+	__gitcomp_nl "$1" "" "" ""
 }
 
 __gitcomp_nl ()
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 40/51] completion: zsh: shuffle __gitcomp* functions
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (38 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 39/51] completion: zsh: simplify __gitcomp_direct Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 41/51] completion: zsh: fix direct quoting Felipe Contreras
                   ` (10 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 10 +++++-----
 1 file changed, 5 insertions(+), 5 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 3619c93ea9..645b4bac31 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -88,11 +88,6 @@ __gitcomp_opts ()
 	compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
 }
 
-__gitcomp_direct ()
-{
-	__gitcomp_nl "$1" "" "" ""
-}
-
 __gitcomp_nl ()
 {
 	emulate -L zsh
@@ -107,6 +102,11 @@ __gitcomp_file ()
 	compadd -f -p "${2-}" -- ${(f)1} && _ret=0
 }
 
+__gitcomp_direct ()
+{
+	__gitcomp_nl "$1" "" "" ""
+}
+
 __gitcomp_file_direct ()
 {
 	__gitcomp_file "$1" ""
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 41/51] completion: zsh: fix direct quoting
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (39 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 40/51] completion: zsh: shuffle __gitcomp* functions Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 42/51] completion: zsh: add elements individually in __gitcomp_opts Felipe Contreras
                   ` (9 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Apparently using "compadd -Q" is almost always wrong, we want zsh to add
quoting when necessary. However, if we remove the -Q option, that would
make zsh add an extra "\ " at the end of some completions.

We can manually remove the spaces from the completions that have them,
and then add the suffix with the -S option, thus there's no more need
for the -Q option.

This makes completions like "stash@{0}" complete correctly:

  git stash show <tab>

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 9 ++++++---
 1 file changed, 6 insertions(+), 3 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 645b4bac31..27ca6efe89 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -55,7 +55,7 @@ __gitcomp ()
 	emulate -L zsh
 
 	local IFS=$' \t\n'
-	compadd -Q -S "${4- }" -p "${2-}" -- ${=1} && _ret=0
+	compadd -S "${4- }" -p "${2-}" -- ${=1} && _ret=0
 }
 
 __gitcomp_opts ()
@@ -85,14 +85,17 @@ __gitcomp_opts ()
 		fi
 		array+=("$c$sfx")
 	done
-	compadd -Q -S '' -p "${2-}" -a -- array && _ret=0
+	compadd -S '' -p "${2-}" -a -- array && _ret=0
 }
 
 __gitcomp_nl ()
 {
 	emulate -L zsh
 
-	compadd -Q -S "${4- }" -p "${2-}" -- ${(f)1} && _ret=0
+	# words that don't end up in space
+	compadd -p "${2-}" -S "${4- }" -q -- ${${(f)1}:#*\ } && _ret=0
+	# words that end in space
+	compadd -p "${2-}" -S " ${4- }" -q -- ${${(M)${(f)1}:#*\ }% } && _ret=0
 }
 
 __gitcomp_file ()
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 42/51] completion: zsh: add elements individually in __gitcomp_opts
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (40 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 41/51] completion: zsh: fix direct quoting Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 43/51] completion: zsh: add __gitcompadd helper Felipe Contreras
                   ` (8 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

It's useful to specify specific suffixes for specific words.

This will be useful later on.

Additionally two tests now pass because we are not using an array
anymore.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 6 ++----
 t/t9904-zsh-completion.sh             | 4 ++--
 2 files changed, 4 insertions(+), 6 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 27ca6efe89..42bf9b95eb 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -67,11 +67,10 @@ __gitcomp_opts ()
 	[[ "$cur_" == *= ]] && return
 
 	local c IFS=$' \t\n' sfx
-	local -a array
 	for c in ${=1}; do
 		if [[ $c == "--" ]]; then
 			[[ "$cur_" == --no-* ]] && continue
-			array+=("--no-... ")
+			compadd -S " " -- "--no-..." && _ret=0
 			break
 		fi
 
@@ -83,9 +82,8 @@ __gitcomp_opts ()
 		else
 			sfx="$4"
 		fi
-		array+=("$c$sfx")
+		compadd -S "$sfx" -p "${2-}" -- "$c" && _ret=0
 	done
-	compadd -S '' -p "${2-}" -a -- array && _ret=0
 }
 
 __gitcomp_nl ()
diff --git a/t/t9904-zsh-completion.sh b/t/t9904-zsh-completion.sh
index 894f3287f4..dc1578f41d 100755
--- a/t/t9904-zsh-completion.sh
+++ b/t/t9904-zsh-completion.sh
@@ -105,7 +105,7 @@ test_expect_success '__gitcomp_opts - option parameter' '
 	EOF
 '
 
-test_expect_failure '__gitcomp_opts - prefix' '
+test_expect_success '__gitcomp_opts - prefix' '
 	test_gitcomp_opts "branch.maint.me" "remote merge mergeoptions rebase" \
 		"branch.maint." "me" <<-\EOF
 	branch.maint.merge Z
@@ -113,7 +113,7 @@ test_expect_failure '__gitcomp_opts - prefix' '
 	EOF
 '
 
-test_expect_failure '__gitcomp_opts - suffix' '
+test_expect_success '__gitcomp_opts - suffix' '
 	test_gitcomp_opts "branch.ma" "master maint next seen" "branch." \
 		"ma" "." <<-\EOF
 	branch.master.Z
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 43/51] completion: zsh: add __gitcompadd helper
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (41 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 42/51] completion: zsh: add elements individually in __gitcomp_opts Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 44/51] completion: zsh: add correct removable suffix Felipe Contreras
                   ` (7 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

So we don't have to do the same over and over.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 12 ++++++++----
 1 file changed, 8 insertions(+), 4 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 42bf9b95eb..e66044ee89 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -50,12 +50,16 @@ COMP_WORDBREAKS=':'
 GIT_SOURCING_ZSH_COMPLETION=y . "$script"
 functions[complete]="$old_complete"
 
+__gitcompadd ()
+{
+	compadd -p "${2-}" -S "${3- }" -- ${=1} && _ret=0
+}
+
 __gitcomp ()
 {
 	emulate -L zsh
 
-	local IFS=$' \t\n'
-	compadd -S "${4- }" -p "${2-}" -- ${=1} && _ret=0
+	IFS=$' \t\n' __gitcompadd "$1" "${2-}" "${4- }"
 }
 
 __gitcomp_opts ()
@@ -70,7 +74,7 @@ __gitcomp_opts ()
 	for c in ${=1}; do
 		if [[ $c == "--" ]]; then
 			[[ "$cur_" == --no-* ]] && continue
-			compadd -S " " -- "--no-..." && _ret=0
+			__gitcompadd "--no-..."
 			break
 		fi
 
@@ -82,7 +86,7 @@ __gitcomp_opts ()
 		else
 			sfx="$4"
 		fi
-		compadd -S "$sfx" -p "${2-}" -- "$c" && _ret=0
+		__gitcompadd "$c" "${2-}" "$sfx"
 	done
 }
 
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 44/51] completion: zsh: add correct removable suffix
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (42 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 43/51] completion: zsh: add __gitcompadd helper Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 45/51] completion: bash: simplify _get_comp_words_by_ref() Felipe Contreras
                   ` (6 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Zsh has a nice feature that allows a suffix to be automatically removed
if followed by a space.

For example:

  git log --prety=

If a space is typed, the suffix '=' is removed.

But we have to set the correct prefix first.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 5 +++--
 1 file changed, 3 insertions(+), 2 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index e66044ee89..7d34522621 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -52,7 +52,7 @@ functions[complete]="$old_complete"
 
 __gitcompadd ()
 {
-	compadd -p "${2-}" -S "${3- }" -- ${=1} && _ret=0
+	compadd -p "${2-}" -S "${3- }" -q -- ${=1} && _ret=0
 }
 
 __gitcomp ()
@@ -80,7 +80,8 @@ __gitcomp_opts ()
 
 		if [[ -z "${4+set}" ]]; then
 			case $c in
-			*=|*.) sfx="" ;;
+			*=) c="${c%=}"; sfx="=" ;;
+			*.) sfx="" ;;
 			*) sfx=" " ;;
 			esac
 		else
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 45/51] completion: bash: simplify _get_comp_words_by_ref()
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (43 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 44/51] completion: zsh: add correct removable suffix Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 46/51] completion: bash: refactor _get_comp_words_by_ref() Felipe Contreras
                   ` (5 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

We don't need the whole functionality of _get_comp_words_by_ref(), we
know exactly what we need from that function, so only do that.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 30 ++++++--------------------
 t/t9902-completion.sh                  | 21 ++++--------------
 2 files changed, 10 insertions(+), 41 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 1fb99265e4..45550f7839 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -413,30 +413,12 @@ __git_reassemble_comp_words_by_ref()
 if ! type _get_comp_words_by_ref >/dev/null 2>&1; then
 _get_comp_words_by_ref ()
 {
-	local exclude cur_ words_ cword_
-	if [ "$1" = "-n" ]; then
-		exclude=$2
-		shift 2
-	fi
-	__git_reassemble_comp_words_by_ref "$exclude"
-	cur_=${words_[cword_]}
-	while [ $# -gt 0 ]; do
-		case "$1" in
-		cur)
-			cur=$cur_
-			;;
-		prev)
-			prev=${words_[$cword_-1]}
-			;;
-		words)
-			words=("${words_[@]}")
-			;;
-		cword)
-			cword=$cword_
-			;;
-		esac
-		shift
-	done
+	local words_ cword_
+	__git_reassemble_comp_words_by_ref "=:"
+	cword=$cword_
+	cur=${words_[cword]}
+	prev=${words_[cword-1]}
+	words=("${words_[@]}")
 }
 fi
 
diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index eb8e173e6b..fc09bafa07 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -40,23 +40,10 @@ GIT_TESTING_PORCELAIN_COMMAND_LIST='add checkout rebase'
 # So let's override it with a minimal version for testing purposes.
 _get_comp_words_by_ref ()
 {
-	while [ $# -gt 0 ]; do
-		case "$1" in
-		cur)
-			cur=${_words[_cword]}
-			;;
-		prev)
-			prev=${_words[_cword-1]}
-			;;
-		words)
-			words=("${_words[@]}")
-			;;
-		cword)
-			cword=$_cword
-			;;
-		esac
-		shift
-	done
+	cword=$_cword
+	cur=${_words[cword]}
+	prev=${_words[cword-1]}
+	words=("${_words[@]}")
 }
 
 print_comp ()
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 46/51] completion: bash: refactor _get_comp_words_by_ref()
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (44 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 45/51] completion: bash: simplify _get_comp_words_by_ref() Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 47/51] completion: bash: cleanup _get_comp_words_by_ref() Felipe Contreras
                   ` (4 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

We don't need a separate function to do what we already know we want to
do.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 93 +++++++++++---------------
 1 file changed, 39 insertions(+), 54 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 45550f7839..4261143d97 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -339,21 +339,11 @@ __git_dequote ()
 #
 #   RELEASE: 2.x
 
-# This function can be used to access a tokenized list of words
-# on the command line:
-#
-#	__git_reassemble_comp_words_by_ref '=:'
-#	if test "${words_[cword_-1]}" = -w
-#	then
-#		...
-#	fi
-#
-# The argument should be a collection of characters from the list of
-# word completion separators (COMP_WORDBREAKS) to treat as ordinary
-# characters.
+# This function reorganizes the words on the command line to be processed by
+# the rest of the script.
 #
 # This is roughly equivalent to going back in time and setting
-# COMP_WORDBREAKS to exclude those characters.  The intent is to
+# COMP_WORDBREAKS to exclude '=' and ':'.  The intent is to
 # make option types like --date=<type> and <rev>:<path> easy to
 # recognize by treating each shell word as a single token.
 #
@@ -361,60 +351,55 @@ __git_dequote ()
 # shared with other completion scripts.  By the time the completion
 # function gets called, COMP_WORDS has already been populated so local
 # changes to COMP_WORDBREAKS have no effect.
-#
-# Output: words_, cword_, cur_.
 
-__git_reassemble_comp_words_by_ref()
+if ! type _get_comp_words_by_ref >/dev/null 2>&1; then
+_get_comp_words_by_ref ()
 {
+	local words_ cword_
 	local exclude i j first
+
 	# Which word separators to exclude?
-	exclude="${1//[^$COMP_WORDBREAKS]}"
+	exclude="${COMP_WORDBREAKS//[^=:]}"
 	cword_=$COMP_CWORD
 	if [ -z "$exclude" ]; then
 		words_=("${COMP_WORDS[@]}")
-		return
-	fi
-	# List of word completion separators has shrunk;
-	# re-assemble words to complete.
-	for ((i=0, j=0; i < ${#COMP_WORDS[@]}; i++, j++)); do
-		# Append each nonempty word consisting of just
-		# word separator characters to the current word.
-		first=t
-		while
-			[ $i -gt 0 ] &&
-			[ -n "${COMP_WORDS[$i]}" ] &&
-			# word consists of excluded word separators
-			[ "${COMP_WORDS[$i]//[^$exclude]}" = "${COMP_WORDS[$i]}" ]
-		do
-			# Attach to the previous token,
-			# unless the previous token is the command name.
-			if [ $j -ge 2 ] && [ -n "$first" ]; then
-				((j--))
-			fi
-			first=
+	else
+		# List of word completion separators has shrunk;
+		# re-assemble words to complete.
+		for ((i=0, j=0; i < ${#COMP_WORDS[@]}; i++, j++)); do
+			# Append each nonempty word consisting of just
+			# word separator characters to the current word.
+			first=t
+			while
+				[ $i -gt 0 ] &&
+				[ -n "${COMP_WORDS[$i]}" ] &&
+				# word consists of excluded word separators
+				[ "${COMP_WORDS[$i]//[^$exclude]}" = "${COMP_WORDS[$i]}" ]
+			do
+				# Attach to the previous token,
+				# unless the previous token is the command name.
+				if [ $j -ge 2 ] && [ -n "$first" ]; then
+					((j--))
+				fi
+				first=
+				words_[$j]=${words_[j]}${COMP_WORDS[i]}
+				if [ $i = $COMP_CWORD ]; then
+					cword_=$j
+				fi
+				if (($i < ${#COMP_WORDS[@]} - 1)); then
+					((i++))
+				else
+					# Done.
+					break 2
+				fi
+			done
 			words_[$j]=${words_[j]}${COMP_WORDS[i]}
 			if [ $i = $COMP_CWORD ]; then
 				cword_=$j
 			fi
-			if (($i < ${#COMP_WORDS[@]} - 1)); then
-				((i++))
-			else
-				# Done.
-				return
-			fi
 		done
-		words_[$j]=${words_[j]}${COMP_WORDS[i]}
-		if [ $i = $COMP_CWORD ]; then
-			cword_=$j
-		fi
-	done
-}
+	fi
 
-if ! type _get_comp_words_by_ref >/dev/null 2>&1; then
-_get_comp_words_by_ref ()
-{
-	local words_ cword_
-	__git_reassemble_comp_words_by_ref "=:"
 	cword=$cword_
 	cur=${words_[cword]}
 	prev=${words_[cword-1]}
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 47/51] completion: bash: cleanup _get_comp_words_by_ref()
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (45 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 46/51] completion: bash: refactor _get_comp_words_by_ref() Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 48/51] completion: bash: trivial cleanup Felipe Contreras
                   ` (3 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Remove temporary variables.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 19 ++++++++-----------
 1 file changed, 8 insertions(+), 11 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 4261143d97..92831977d7 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -355,14 +355,13 @@ __git_dequote ()
 if ! type _get_comp_words_by_ref >/dev/null 2>&1; then
 _get_comp_words_by_ref ()
 {
-	local words_ cword_
 	local exclude i j first
 
 	# Which word separators to exclude?
 	exclude="${COMP_WORDBREAKS//[^=:]}"
-	cword_=$COMP_CWORD
+	cword=$COMP_CWORD
 	if [ -z "$exclude" ]; then
-		words_=("${COMP_WORDS[@]}")
+		words=("${COMP_WORDS[@]}")
 	else
 		# List of word completion separators has shrunk;
 		# re-assemble words to complete.
@@ -382,9 +381,9 @@ _get_comp_words_by_ref ()
 					((j--))
 				fi
 				first=
-				words_[$j]=${words_[j]}${COMP_WORDS[i]}
+				words[$j]=${words[j]}${COMP_WORDS[i]}
 				if [ $i = $COMP_CWORD ]; then
-					cword_=$j
+					cword=$j
 				fi
 				if (($i < ${#COMP_WORDS[@]} - 1)); then
 					((i++))
@@ -393,17 +392,15 @@ _get_comp_words_by_ref ()
 					break 2
 				fi
 			done
-			words_[$j]=${words_[j]}${COMP_WORDS[i]}
+			words[$j]=${words[j]}${COMP_WORDS[i]}
 			if [ $i = $COMP_CWORD ]; then
-				cword_=$j
+				cword=$j
 			fi
 		done
 	fi
 
-	cword=$cword_
-	cur=${words_[cword]}
-	prev=${words_[cword-1]}
-	words=("${words_[@]}")
+	cur=${words[cword]}
+	prev=${words[cword-1]}
 }
 fi
 
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 48/51] completion: bash: trivial cleanup
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (46 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 47/51] completion: bash: cleanup _get_comp_words_by_ref() Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 49/51] completion: bash: rename _get_comp_words_by_ref() Felipe Contreras
                   ` (2 subsequent siblings)
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

The most typical case first (COMP_WORDBREAKS contains our wanted words).

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 6 +++---
 1 file changed, 3 insertions(+), 3 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 92831977d7..395a356106 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -360,9 +360,7 @@ _get_comp_words_by_ref ()
 	# Which word separators to exclude?
 	exclude="${COMP_WORDBREAKS//[^=:]}"
 	cword=$COMP_CWORD
-	if [ -z "$exclude" ]; then
-		words=("${COMP_WORDS[@]}")
-	else
+	if [ -n "$exclude" ]; then
 		# List of word completion separators has shrunk;
 		# re-assemble words to complete.
 		for ((i=0, j=0; i < ${#COMP_WORDS[@]}; i++, j++)); do
@@ -397,6 +395,8 @@ _get_comp_words_by_ref ()
 				cword=$j
 			fi
 		done
+	else
+		words=("${COMP_WORDS[@]}")
 	fi
 
 	cur=${words[cword]}
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 49/51] completion: bash: rename _get_comp_words_by_ref()
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (47 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 48/51] completion: bash: trivial cleanup Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 50/51] zsh: remove version Felipe Contreras
  2022-08-30  9:31 ` [PATCH 51/51] completion: bash: trivial grammar fix Felipe Contreras
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

It's only used in one place, rename it, and use it even if
bash-completion's more inefficient version of _get_comp_words_by_ref()
is available.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 186 ++++++++++++-------------
 t/t9902-completion.sh                  |   2 +-
 2 files changed, 94 insertions(+), 94 deletions(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 395a356106..77a475e272 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -312,98 +312,6 @@ __git_dequote ()
 	done
 }
 
-# The following function is based on code from:
-#
-#   bash_completion - programmable completion functions for bash 3.2+
-#
-#   Copyright © 2006-2008, Ian Macdonald <ian@caliban.org>
-#             © 2009-2010, Bash Completion Maintainers
-#                     <bash-completion-devel@lists.alioth.debian.org>
-#
-#   This program is free software; you can redistribute it and/or modify
-#   it under the terms of the GNU General Public License as published by
-#   the Free Software Foundation; either version 2, or (at your option)
-#   any later version.
-#
-#   This program is distributed in the hope that it will be useful,
-#   but WITHOUT ANY WARRANTY; without even the implied warranty of
-#   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-#   GNU General Public License for more details.
-#
-#   You should have received a copy of the GNU General Public License
-#   along with this program; if not, see <http://www.gnu.org/licenses/>.
-#
-#   The latest version of this software can be obtained here:
-#
-#   http://bash-completion.alioth.debian.org/
-#
-#   RELEASE: 2.x
-
-# This function reorganizes the words on the command line to be processed by
-# the rest of the script.
-#
-# This is roughly equivalent to going back in time and setting
-# COMP_WORDBREAKS to exclude '=' and ':'.  The intent is to
-# make option types like --date=<type> and <rev>:<path> easy to
-# recognize by treating each shell word as a single token.
-#
-# It is best not to set COMP_WORDBREAKS directly because the value is
-# shared with other completion scripts.  By the time the completion
-# function gets called, COMP_WORDS has already been populated so local
-# changes to COMP_WORDBREAKS have no effect.
-
-if ! type _get_comp_words_by_ref >/dev/null 2>&1; then
-_get_comp_words_by_ref ()
-{
-	local exclude i j first
-
-	# Which word separators to exclude?
-	exclude="${COMP_WORDBREAKS//[^=:]}"
-	cword=$COMP_CWORD
-	if [ -n "$exclude" ]; then
-		# List of word completion separators has shrunk;
-		# re-assemble words to complete.
-		for ((i=0, j=0; i < ${#COMP_WORDS[@]}; i++, j++)); do
-			# Append each nonempty word consisting of just
-			# word separator characters to the current word.
-			first=t
-			while
-				[ $i -gt 0 ] &&
-				[ -n "${COMP_WORDS[$i]}" ] &&
-				# word consists of excluded word separators
-				[ "${COMP_WORDS[$i]//[^$exclude]}" = "${COMP_WORDS[$i]}" ]
-			do
-				# Attach to the previous token,
-				# unless the previous token is the command name.
-				if [ $j -ge 2 ] && [ -n "$first" ]; then
-					((j--))
-				fi
-				first=
-				words[$j]=${words[j]}${COMP_WORDS[i]}
-				if [ $i = $COMP_CWORD ]; then
-					cword=$j
-				fi
-				if (($i < ${#COMP_WORDS[@]} - 1)); then
-					((i++))
-				else
-					# Done.
-					break 2
-				fi
-			done
-			words[$j]=${words[j]}${COMP_WORDS[i]}
-			if [ $i = $COMP_CWORD ]; then
-				cword=$j
-			fi
-		done
-	else
-		words=("${COMP_WORDS[@]}")
-	fi
-
-	cur=${words[cword]}
-	prev=${words[cword-1]}
-}
-fi
-
 # Clear the variables caching builtins' options when (re-)sourcing
 # the completion script.
 if [[ -n ${ZSH_VERSION-} ]]; then
@@ -3477,10 +3385,102 @@ if [[ -n ${ZSH_VERSION-} && -z ${GIT_SOURCING_ZSH_COMPLETION-} ]]; then
 	return
 fi
 
+# The following function is based on code from:
+#
+#   bash_completion - programmable completion functions for bash 3.2+
+#
+#   Copyright © 2006-2008, Ian Macdonald <ian@caliban.org>
+#             © 2009-2010, Bash Completion Maintainers
+#                     <bash-completion-devel@lists.alioth.debian.org>
+#
+#   This program is free software; you can redistribute it and/or modify
+#   it under the terms of the GNU General Public License as published by
+#   the Free Software Foundation; either version 2, or (at your option)
+#   any later version.
+#
+#   This program is distributed in the hope that it will be useful,
+#   but WITHOUT ANY WARRANTY; without even the implied warranty of
+#   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+#   GNU General Public License for more details.
+#
+#   You should have received a copy of the GNU General Public License
+#   along with this program; if not, see <http://www.gnu.org/licenses/>.
+#
+#   The latest version of this software can be obtained here:
+#
+#   http://bash-completion.alioth.debian.org/
+#
+#   RELEASE: 2.x
+
+# This function reorganizes the words on the command line to be processed by
+# the rest of the script.
+#
+# This is roughly equivalent to going back in time and setting
+# COMP_WORDBREAKS to exclude '=' and ':'.  The intent is to
+# make option types like --date=<type> and <rev>:<path> easy to
+# recognize by treating each shell word as a single token.
+#
+# It is best not to set COMP_WORDBREAKS directly because the value is
+# shared with other completion scripts.  By the time the completion
+# function gets called, COMP_WORDS has already been populated so local
+# changes to COMP_WORDBREAKS have no effect.
+
+if ! type __git_get_comp_words_by_ref >/dev/null 2>&1; then
+__git_get_comp_words_by_ref ()
+{
+	local exclude i j first
+
+	# Which word separators to exclude?
+	exclude="${COMP_WORDBREAKS//[^=:]}"
+	cword=$COMP_CWORD
+	if [ -n "$exclude" ]; then
+		# List of word completion separators has shrunk;
+		# re-assemble words to complete.
+		for ((i=0, j=0; i < ${#COMP_WORDS[@]}; i++, j++)); do
+			# Append each nonempty word consisting of just
+			# word separator characters to the current word.
+			first=t
+			while
+				[ $i -gt 0 ] &&
+				[ -n "${COMP_WORDS[$i]}" ] &&
+				# word consists of excluded word separators
+				[ "${COMP_WORDS[$i]//[^$exclude]}" = "${COMP_WORDS[$i]}" ]
+			do
+				# Attach to the previous token,
+				# unless the previous token is the command name.
+				if [ $j -ge 2 ] && [ -n "$first" ]; then
+					((j--))
+				fi
+				first=
+				words[$j]=${words[j]}${COMP_WORDS[i]}
+				if [ $i = $COMP_CWORD ]; then
+					cword=$j
+				fi
+				if (($i < ${#COMP_WORDS[@]} - 1)); then
+					((i++))
+				else
+					# Done.
+					break 2
+				fi
+			done
+			words[$j]=${words[j]}${COMP_WORDS[i]}
+			if [ $i = $COMP_CWORD ]; then
+				cword=$j
+			fi
+		done
+	else
+		words=("${COMP_WORDS[@]}")
+	fi
+
+	cur=${words[cword]}
+	prev=${words[cword-1]}
+}
+fi
+
 __git_func_wrap ()
 {
 	local cur words cword prev __git_cmd_idx=0
-	_get_comp_words_by_ref -n =: cur words cword prev
+	__git_get_comp_words_by_ref
 	$1
 }
 
diff --git a/t/t9902-completion.sh b/t/t9902-completion.sh
index fc09bafa07..fff8451716 100755
--- a/t/t9902-completion.sh
+++ b/t/t9902-completion.sh
@@ -38,7 +38,7 @@ GIT_TESTING_PORCELAIN_COMMAND_LIST='add checkout rebase'
 # We don't need this function to actually join words or do anything special.
 # Also, it's cleaner to avoid touching bash's internal completion variables.
 # So let's override it with a minimal version for testing purposes.
-_get_comp_words_by_ref ()
+__git_get_comp_words_by_ref ()
 {
 	cword=$_cword
 	cur=${_words[cword]}
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 50/51] zsh: remove version
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (48 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 49/51] completion: bash: rename _get_comp_words_by_ref() Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  2022-08-30  9:31 ` [PATCH 51/51] completion: bash: trivial grammar fix Felipe Contreras
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Doesn't seem to be useful.

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.zsh | 5 -----
 1 file changed, 5 deletions(-)

diff --git a/contrib/completion/git-completion.zsh b/contrib/completion/git-completion.zsh
index 7d34522621..31bf88c1c5 100644
--- a/contrib/completion/git-completion.zsh
+++ b/contrib/completion/git-completion.zsh
@@ -118,11 +118,6 @@ __gitcomp_file_direct ()
 	__gitcomp_file "$1" ""
 }
 
-_git_zsh ()
-{
-	__gitcomp "v1.1"
-}
-
 __git_complete_command ()
 {
 	emulate -L zsh
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

* [PATCH 51/51] completion: bash: trivial grammar fix
  2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
                   ` (49 preceding siblings ...)
  2022-08-30  9:31 ` [PATCH 50/51] zsh: remove version Felipe Contreras
@ 2022-08-30  9:31 ` Felipe Contreras
  50 siblings, 0 replies; 52+ messages in thread
From: Felipe Contreras @ 2022-08-30  9:31 UTC (permalink / raw)
  To: git; +Cc: git-fc, Felipe Contreras

Signed-off-by: Felipe Contreras <felipe.contreras@gmail.com>
---
 contrib/completion/git-completion.bash | 2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/contrib/completion/git-completion.bash b/contrib/completion/git-completion.bash
index 77a475e272..dffb34266f 100644
--- a/contrib/completion/git-completion.bash
+++ b/contrib/completion/git-completion.bash
@@ -3152,7 +3152,7 @@ _git_worktree ()
 		# Here we are not completing an --option, it's either the
 		# path or a ref.
 		case "$prev" in
-		-b|-B)	# Complete refs for branch to be created/reseted.
+		-b|-B)	# Complete refs for branch to be created/reset.
 			__git_complete_refs
 			;;
 		-*)	# The previous word is an -o|--option without an
-- 
2.37.2.351.g9bf691b78c.dirty


^ permalink raw reply related	[flat|nested] 52+ messages in thread

end of thread, other threads:[~2022-08-30  9:35 UTC | newest]

Thread overview: 52+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-08-30  9:30 [PATCH 00/51] completion: revamp Felipe Contreras
2022-08-30  9:30 ` [PATCH 01/51] test: completion add test for __git_cmd_idx Felipe Contreras
2022-08-30  9:30 ` [PATCH 02/51] test: add zsh completion tests Felipe Contreras
2022-08-30  9:30 ` [PATCH 03/51] completion: fix __git_cmd_idx regression for zsh Felipe Contreras
2022-08-30  9:30 ` [PATCH 04/51] completion: bash: trivial cleanup Felipe Contreras
2022-08-30  9:30 ` [PATCH 05/51] completion: zsh: add higher-priority location Felipe Contreras
2022-08-30  9:30 ` [PATCH 06/51] zsh: resolve symlink of script Felipe Contreras
2022-08-30  9:30 ` [PATCH 07/51] zsh: simplify realpath dirname idiom Felipe Contreras
2022-08-30  9:30 ` [PATCH 08/51] test: reset environment variables Felipe Contreras
2022-08-30  9:30 ` [PATCH 09/51] completion: prompt: use generic colors Felipe Contreras
2022-08-30  9:30 ` [PATCH 10/51] completion: fix for suboptions with value Felipe Contreras
2022-08-30  9:30 ` [PATCH 11/51] completion: zsh: trivial improvement Felipe Contreras
2022-08-30  9:30 ` [PATCH 12/51] completion: bash: do not modify COMP_WORDBREAKS Felipe Contreras
2022-08-30  9:31 ` [PATCH 13/51] test: completion: fix currently typed words Felipe Contreras
2022-08-30  9:31 ` [PATCH 14/51] test: completion: switch __gitcomp_nl prefix test Felipe Contreras
2022-08-30  9:31 ` [PATCH 15/51] test: completion: add run_func() helper Felipe Contreras
2022-08-30  9:31 ` [PATCH 16/51] completion: bash: remove non-append functionality Felipe Contreras
2022-08-30  9:31 ` [PATCH 17/51] completion: bash: get rid of _append() functions Felipe Contreras
2022-08-30  9:31 ` [PATCH 18/51] completion: bash: get rid of any non-append code Felipe Contreras
2022-08-30  9:31 ` [PATCH 19/51] completion: zsh: fix options with arguments Felipe Contreras
2022-08-30  9:31 ` [PATCH 20/51] completion: zsh: expand --git-dir file argument Felipe Contreras
2022-08-30  9:31 ` [PATCH 21/51] completion: zsh: add support for general -C opts Felipe Contreras
2022-08-30  9:31 ` [PATCH 22/51] completion: zsh: fix for undefined completions Felipe Contreras
2022-08-30  9:31 ` [PATCH 23/51] completion: zsh: add support for general -c opts Felipe Contreras
2022-08-30  9:31 ` [PATCH 24/51] completion: zsh: fix extra space on foo= Felipe Contreras
2022-08-30  9:31 ` [PATCH 25/51] completion: zsh: add excluded options Felipe Contreras
2022-08-30  9:31 ` [PATCH 26/51] completion: zsh: always set compset Felipe Contreras
2022-08-30  9:31 ` [PATCH 27/51] completion: factor out check in __gitcomp Felipe Contreras
2022-08-30  9:31 ` [PATCH 28/51] completion: simplify equal suffix check Felipe Contreras
2022-08-30  9:31 ` [PATCH 29/51] completion: refactor __gitcomp Felipe Contreras
2022-08-30  9:31 ` [PATCH 30/51] completion: simplify __gitcomp Felipe Contreras
2022-08-30  9:31 ` [PATCH 31/51] completion: bash: change suffix check in __gitcomp Felipe Contreras
2022-08-30  9:31 ` [PATCH 32/51] completion: improve __gitcomp suffix code Felipe Contreras
2022-08-30  9:31 ` [PATCH 33/51] test: completion: add missing test Felipe Contreras
2022-08-30  9:31 ` [PATCH 34/51] completion: bash: simplify config_variable_name Felipe Contreras
2022-08-30  9:31 ` [PATCH 35/51] completion: bash: improve __gitcomp description Felipe Contreras
2022-08-30  9:31 ` [PATCH 36/51] completion: add __gitcomp_opts Felipe Contreras
2022-08-30  9:31 ` [PATCH 37/51] completion: bash: cleanup __gitcomp* invocations Felipe Contreras
2022-08-30  9:31 ` [PATCH 38/51] completion: bash: shuffle __gitcomp functions Felipe Contreras
2022-08-30  9:31 ` [PATCH 39/51] completion: zsh: simplify __gitcomp_direct Felipe Contreras
2022-08-30  9:31 ` [PATCH 40/51] completion: zsh: shuffle __gitcomp* functions Felipe Contreras
2022-08-30  9:31 ` [PATCH 41/51] completion: zsh: fix direct quoting Felipe Contreras
2022-08-30  9:31 ` [PATCH 42/51] completion: zsh: add elements individually in __gitcomp_opts Felipe Contreras
2022-08-30  9:31 ` [PATCH 43/51] completion: zsh: add __gitcompadd helper Felipe Contreras
2022-08-30  9:31 ` [PATCH 44/51] completion: zsh: add correct removable suffix Felipe Contreras
2022-08-30  9:31 ` [PATCH 45/51] completion: bash: simplify _get_comp_words_by_ref() Felipe Contreras
2022-08-30  9:31 ` [PATCH 46/51] completion: bash: refactor _get_comp_words_by_ref() Felipe Contreras
2022-08-30  9:31 ` [PATCH 47/51] completion: bash: cleanup _get_comp_words_by_ref() Felipe Contreras
2022-08-30  9:31 ` [PATCH 48/51] completion: bash: trivial cleanup Felipe Contreras
2022-08-30  9:31 ` [PATCH 49/51] completion: bash: rename _get_comp_words_by_ref() Felipe Contreras
2022-08-30  9:31 ` [PATCH 50/51] zsh: remove version Felipe Contreras
2022-08-30  9:31 ` [PATCH 51/51] completion: bash: trivial grammar fix Felipe Contreras

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).