diff options
Diffstat (limited to 't')
103 files changed, 1692 insertions, 796 deletions
diff --git a/t/helper/test-run-command.c b/t/helper/test-run-command.c index 3da8525ce6..f3b90aa834 100644 --- a/t/helper/test-run-command.c +++ b/t/helper/test-run-command.c @@ -19,7 +19,6 @@ #include "thread-utils.h" #include "wildmatch.h" #include "gettext.h" -#include "parse-options.h" static int number_callbacks; static int parallel_next(struct child_process *cp, diff --git a/t/perf/p1006-cat-file.sh b/t/perf/p1006-cat-file.sh new file mode 100755 index 0000000000..dcd8015379 --- /dev/null +++ b/t/perf/p1006-cat-file.sh @@ -0,0 +1,12 @@ +#!/bin/sh + +test_description='Tests listing object info performance' +. ./perf-lib.sh + +test_perf_large_repo + +test_perf 'cat-file --batch-check' ' + git cat-file --batch-all-objects --batch-check +' + +test_done diff --git a/t/t0000-basic.sh b/t/t0000-basic.sh index 9dcbf518a7..17a268ccd1 100755 --- a/t/t0000-basic.sh +++ b/t/t0000-basic.sh @@ -101,6 +101,19 @@ test_expect_success 'subtest: 2/3 tests passing' ' EOF ' +test_expect_success 'subtest: --immediate' ' + run_sub_test_lib_test_err partial-pass \ + --immediate && + check_sub_test_lib_test_err partial-pass \ + <<-\EOF_OUT 3<<-EOF_ERR + > ok 1 - passing test #1 + > not ok 2 - failing test #2 + > # false + > 1..2 + EOF_OUT + EOF_ERR +' + test_expect_success 'subtest: a failing TODO test' ' write_and_run_sub_test_lib_test failing-todo <<-\EOF && test_expect_success "passing test" "true" diff --git a/t/t0029-core-unsetenvvars.sh b/t/t0029-core-unsetenvvars.sh index b138e1d9cb..4e8e90dd98 100755 --- a/t/t0029-core-unsetenvvars.sh +++ b/t/t0029-core-unsetenvvars.sh @@ -12,8 +12,7 @@ then fi test_expect_success 'setup' ' - mkdir -p "$TRASH_DIRECTORY/.git/hooks" && - write_script "$TRASH_DIRECTORY/.git/hooks/pre-commit" <<-\EOF + test_hook --setup pre-commit <<-\EOF echo $HOBBES >&2 EOF ' diff --git a/t/t0091-bugreport.sh b/t/t0091-bugreport.sh index eeedbfa919..08f5fe9cae 100755 --- a/t/t0091-bugreport.sh +++ b/t/t0091-bugreport.sh @@ -60,18 +60,22 @@ test_expect_success 'can create leading directories outside of a git dir' ' test_expect_success 'indicates populated hooks' ' test_when_finished rm git-bugreport-hooks.txt && - test_when_finished rm -fr .git/hooks && - rm -fr .git/hooks && - mkdir .git/hooks && - for hook in applypatch-msg prepare-commit-msg.sample - do - write_script ".git/hooks/$hook" <<-EOF || return 1 - echo "hook $hook exists" - EOF - done && + + test_hook applypatch-msg <<-\EOF && + true + EOF + test_hook unknown-hook <<-\EOF && + true + EOF git bugreport -s hooks && - grep applypatch-msg git-bugreport-hooks.txt && - ! grep prepare-commit-msg git-bugreport-hooks.txt + + sort >expect <<-\EOF && + [Enabled Hooks] + applypatch-msg + EOF + + sed -ne "/^\[Enabled Hooks\]$/,/^$/p" <git-bugreport-hooks.txt >actual && + test_cmp expect actual ' test_done diff --git a/t/t0410-partial-clone.sh b/t/t0410-partial-clone.sh index f17abd298c..1e864cf317 100755 --- a/t/t0410-partial-clone.sh +++ b/t/t0410-partial-clone.sh @@ -618,6 +618,25 @@ test_expect_success 'do not fetch when checking existence of tree we construct o git -C repo cherry-pick side1 ' +test_expect_success 'exact rename does not need to fetch the blob lazily' ' + rm -rf repo partial.git && + test_create_repo repo && + content="some dummy content" && + test_commit -C repo create-a-file file.txt "$content" && + git -C repo mv file.txt new-file.txt && + git -C repo commit -m rename-the-file && + FILE_HASH=$(git -C repo rev-parse HEAD:new-file.txt) && + test_config -C repo uploadpack.allowfilter 1 && + test_config -C repo uploadpack.allowanysha1inwant 1 && + + git clone --filter=blob:none --bare "file://$(pwd)/repo" partial.git && + git -C partial.git rev-list --objects --missing=print HEAD >out && + grep "[?]$FILE_HASH" out && + git -C partial.git log --follow -- new-file.txt && + git -C partial.git rev-list --objects --missing=print HEAD >out && + grep "[?]$FILE_HASH" out +' + test_expect_success 'lazy-fetch when accessing object not in the_repository' ' rm -rf full partial.git && test_create_repo full && diff --git a/t/t1092-sparse-checkout-compatibility.sh b/t/t1092-sparse-checkout-compatibility.sh index dcc0a30d4a..236ab53028 100755 --- a/t/t1092-sparse-checkout-compatibility.sh +++ b/t/t1092-sparse-checkout-compatibility.sh @@ -16,7 +16,9 @@ test_expect_success 'setup' ' echo "after deep" >e && echo "after folder1" >g && echo "after x" >z && - mkdir folder1 folder2 deep x && + mkdir folder1 folder2 deep before x && + echo "before deep" >before/a && + echo "before deep again" >before/b && mkdir deep/deeper1 deep/deeper2 deep/before deep/later && mkdir deep/deeper1/deepest && mkdir deep/deeper1/deepest2 && @@ -254,6 +256,7 @@ test_expect_success 'root directory cannot be sparse' ' # Verify sparse directories still present, root directory is not sparse cat >expect <<-EOF && + before/ folder1/ folder2/ x/ @@ -1444,6 +1447,7 @@ test_expect_success 'ls-files' ' cat >expect <<-\EOF && a + before/ deep/ e folder1- @@ -1491,6 +1495,7 @@ test_expect_success 'ls-files' ' cat >expect <<-\EOF && a + before/ deep/ e folder1- diff --git a/t/t1350-config-hooks-path.sh b/t/t1350-config-hooks-path.sh index fa9647a7c0..f6dc83e2aa 100755 --- a/t/t1350-config-hooks-path.sh +++ b/t/t1350-config-hooks-path.sh @@ -6,11 +6,11 @@ test_description='Test the core.hooksPath configuration variable' test_expect_success 'set up a pre-commit hook in core.hooksPath' ' >actual && - mkdir -p .git/custom-hooks .git/hooks && + mkdir -p .git/custom-hooks && write_script .git/custom-hooks/pre-commit <<-\EOF && echo CUSTOM >>actual EOF - write_script .git/hooks/pre-commit <<-\EOF + test_hook --setup pre-commit <<-\EOF echo NORMAL >>actual EOF ' diff --git a/t/t1410-reflog.sh b/t/t1410-reflog.sh index 68f69bb543..aa59954f6c 100755 --- a/t/t1410-reflog.sh +++ b/t/t1410-reflog.sh @@ -106,6 +106,28 @@ test_expect_success setup ' test_line_count = 4 output ' +test_expect_success 'correct usage on sub-command -h' ' + test_expect_code 129 git reflog expire -h >err && + grep "git reflog expire" err +' + +test_expect_success 'correct usage on "git reflog show -h"' ' + test_expect_code 129 git reflog show -h >err && + grep -F "git reflog [show]" err +' + +test_expect_success 'pass through -- to sub-command' ' + test_when_finished "rm -rf repo" && + git init repo && + test_commit -C repo message --a-file contents dash-tag && + + git -C repo reflog show -- --does-not-exist >out && + test_must_be_empty out && + git -C repo reflog show >expect && + git -C repo reflog show -- --a-file >actual && + test_cmp expect actual +' + test_expect_success rewind ' test_tick && git reset --hard HEAD~2 && test -f C && @@ -423,4 +445,13 @@ test_expect_success 'expire with multiple worktrees' ' ) ' +test_expect_success REFFILES 'empty reflog' ' + test_when_finished "rm -rf empty" && + git init empty && + test_commit -C empty A && + >empty/.git/logs/refs/heads/foo && + git -C empty reflog expire --all 2>err && + test_must_be_empty err +' + test_done diff --git a/t/t1411-reflog-show.sh b/t/t1411-reflog-show.sh index 0bb319b944..975c4ea83a 100755 --- a/t/t1411-reflog-show.sh +++ b/t/t1411-reflog-show.sh @@ -169,9 +169,4 @@ test_expect_success 'git log -g -p shows diffs vs. parents' ' test_cmp expect actual ' -test_expect_success 'reflog exists works' ' - git reflog exists refs/heads/main && - ! git reflog exists refs/heads/nonexistent -' - test_done diff --git a/t/t1416-ref-transaction-hooks.sh b/t/t1416-ref-transaction-hooks.sh index 4e1e84a91f..085a7a46f2 100755 --- a/t/t1416-ref-transaction-hooks.sh +++ b/t/t1416-ref-transaction-hooks.sh @@ -8,7 +8,6 @@ export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME . ./test-lib.sh test_expect_success setup ' - mkdir -p .git/hooks && test_commit PRE && PRE_OID=$(git rev-parse PRE) && test_commit POST && @@ -16,9 +15,8 @@ test_expect_success setup ' ' test_expect_success 'hook allows updating ref if successful' ' - test_when_finished "rm .git/hooks/reference-transaction" && git reset --hard PRE && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && echo "$*" >>actual EOF cat >expect <<-EOF && @@ -30,9 +28,8 @@ test_expect_success 'hook allows updating ref if successful' ' ' test_expect_success 'hook aborts updating ref in prepared state' ' - test_when_finished "rm .git/hooks/reference-transaction" && git reset --hard PRE && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && if test "$1" = prepared then exit 1 @@ -43,9 +40,9 @@ test_expect_success 'hook aborts updating ref in prepared state' ' ' test_expect_success 'hook gets all queued updates in prepared state' ' - test_when_finished "rm .git/hooks/reference-transaction actual" && + test_when_finished "rm actual" && git reset --hard PRE && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && if test "$1" = prepared then while read -r line @@ -66,9 +63,9 @@ test_expect_success 'hook gets all queued updates in prepared state' ' ' test_expect_success 'hook gets all queued updates in committed state' ' - test_when_finished "rm .git/hooks/reference-transaction actual" && + test_when_finished "rm actual" && git reset --hard PRE && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && if test "$1" = committed then while read -r line @@ -86,9 +83,9 @@ test_expect_success 'hook gets all queued updates in committed state' ' ' test_expect_success 'hook gets all queued updates in aborted state' ' - test_when_finished "rm .git/hooks/reference-transaction actual" && + test_when_finished "rm actual" && git reset --hard PRE && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && if test "$1" = aborted then while read -r line @@ -115,11 +112,11 @@ test_expect_success 'interleaving hook calls succeed' ' git init --bare target-repo.git && - write_script target-repo.git/hooks/reference-transaction <<-\EOF && + test_hook -C target-repo.git reference-transaction <<-\EOF && echo $0 "$@" >>actual EOF - write_script target-repo.git/hooks/update <<-\EOF && + test_hook -C target-repo.git update <<-\EOF && echo $0 "$@" >>actual EOF @@ -140,7 +137,7 @@ test_expect_success 'hook does not get called on packing refs' ' # Pack references first such that we are in a known state. git pack-refs --all && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && echo "$@" >>actual cat >>actual EOF @@ -166,7 +163,7 @@ test_expect_success 'deleting packed ref calls hook once' ' git update-ref refs/heads/to-be-deleted $POST_OID && git pack-refs --all && - write_script .git/hooks/reference-transaction <<-\EOF && + test_hook reference-transaction <<-\EOF && echo "$@" >>actual cat >>actual EOF diff --git a/t/t1418-reflog-exists.sh b/t/t1418-reflog-exists.sh new file mode 100755 index 0000000000..d51ecd5e92 --- /dev/null +++ b/t/t1418-reflog-exists.sh @@ -0,0 +1,37 @@ +#!/bin/sh + +test_description='Test reflog display routines' +GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME=main +export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME + +. ./test-lib.sh + +test_expect_success 'setup' ' + test_commit A +' + +test_expect_success 'usage' ' + test_expect_code 129 git reflog exists && + test_expect_code 129 git reflog exists -h +' + +test_expect_success 'usage: unknown option' ' + test_expect_code 129 git reflog exists --unknown-option +' + +test_expect_success 'reflog exists works' ' + git reflog exists refs/heads/main && + test_must_fail git reflog exists refs/heads/nonexistent +' + +test_expect_success 'reflog exists works with a "--" delimiter' ' + git reflog exists -- refs/heads/main && + test_must_fail git reflog exists -- refs/heads/nonexistent +' + +test_expect_success 'reflog exists works with a "--end-of-options" delimiter' ' + git reflog exists --end-of-options refs/heads/main && + test_must_fail git reflog exists --end-of-options refs/heads/nonexistent +' + +test_done diff --git a/t/t1800-hook.sh b/t/t1800-hook.sh index 29718aa991..26ed5e11bc 100755 --- a/t/t1800-hook.sh +++ b/t/t1800-hook.sh @@ -27,7 +27,7 @@ test_expect_success 'git hook run: nonexistent hook with --ignore-missing' ' ' test_expect_success 'git hook run: basic' ' - write_script .git/hooks/test-hook <<-EOF && + test_hook test-hook <<-EOF && echo Test hook EOF @@ -39,7 +39,7 @@ test_expect_success 'git hook run: basic' ' ' test_expect_success 'git hook run: stdout and stderr both write to our stderr' ' - write_script .git/hooks/test-hook <<-EOF && + test_hook test-hook <<-EOF && echo >&1 Will end up on stderr echo >&2 Will end up on stderr EOF @@ -53,38 +53,23 @@ test_expect_success 'git hook run: stdout and stderr both write to our stderr' ' test_must_be_empty stdout.actual ' -test_expect_success 'git hook run: exit codes are passed along' ' - write_script .git/hooks/test-hook <<-EOF && - exit 1 - EOF - - test_expect_code 1 git hook run test-hook && - - write_script .git/hooks/test-hook <<-EOF && - exit 2 - EOF - - test_expect_code 2 git hook run test-hook && - - write_script .git/hooks/test-hook <<-EOF && - exit 128 - EOF +for code in 1 2 128 129 +do + test_expect_success "git hook run: exit code $code is passed along" ' + test_hook test-hook <<-EOF && + exit $code + EOF - test_expect_code 128 git hook run test-hook && - - write_script .git/hooks/test-hook <<-EOF && - exit 129 - EOF - - test_expect_code 129 git hook run test-hook -' + test_expect_code $code git hook run test-hook + ' +done test_expect_success 'git hook run arg u ments without -- is not allowed' ' test_expect_code 129 git hook run test-hook arg u ments ' test_expect_success 'git hook run -- pass arguments' ' - write_script .git/hooks/test-hook <<-\EOF && + test_hook test-hook <<-\EOF && echo $1 echo $2 EOF @@ -99,7 +84,7 @@ test_expect_success 'git hook run -- pass arguments' ' ' test_expect_success 'git hook run -- out-of-repo runs excluded' ' - write_script .git/hooks/test-hook <<-EOF && + test_hook test-hook <<-EOF && echo Test hook EOF @@ -120,6 +105,10 @@ test_expect_success 'git -c core.hooksPath=<PATH> hook run' ' Hook ran four EOF + test_hook test-hook <<-EOF && + echo Test hook + EOF + # Test various ways of specifying the path. See also # t1350-config-hooks-path.sh >actual && diff --git a/t/t2400-worktree-add.sh b/t/t2400-worktree-add.sh index 43139af08f..2f564d533d 100755 --- a/t/t2400-worktree-add.sh +++ b/t/t2400-worktree-add.sh @@ -559,10 +559,7 @@ test_expect_success 'git worktree --no-guess-remote option overrides config' ' ' post_checkout_hook () { - gitdir=${1:-.git} - test_when_finished "rm -f $gitdir/hooks/post-checkout" && - mkdir -p $gitdir/hooks && - write_script $gitdir/hooks/post-checkout <<-\EOF + test_hook -C "$1" post-checkout <<-\EOF { echo $* git rev-parse --git-dir --show-toplevel diff --git a/t/t3101-ls-tree-dirname.sh b/t/t3101-ls-tree-dirname.sh index 05fde64225..217006d1bf 100755 --- a/t/t3101-ls-tree-dirname.sh +++ b/t/t3101-ls-tree-dirname.sh @@ -201,31 +201,34 @@ EOF test_cmp expected check ' -test_expect_success 'ls-tree --name-only' ' - git ls-tree --name-only $tree >current && - cat >expected <<\EOF && -1.txt -2.txt -path0 -path1 -path2 -path3 -EOF - test_output -' - -test_expect_success 'ls-tree --name-only -r' ' - git ls-tree --name-only -r $tree >current && - cat >expected <<\EOF && -1.txt -2.txt -path0/a/b/c/1.txt -path1/b/c/1.txt -path2/1.txt -path3/1.txt -path3/2.txt -EOF - test_output -' +for opt in --name-only --name-status +do + test_expect_success "ls-tree $opt" ' + git ls-tree $opt $tree >current && + cat >expected <<-\EOF && + 1.txt + 2.txt + path0 + path1 + path2 + path3 + EOF + test_output + ' + + test_expect_success "ls-tree $opt -r" ' + git ls-tree $opt -r $tree >current && + cat >expected <<-\EOF && + 1.txt + 2.txt + path0/a/b/c/1.txt + path1/b/c/1.txt + path2/1.txt + path3/1.txt + path3/2.txt + EOF + test_output + ' +done test_done diff --git a/t/t3103-ls-tree-misc.sh b/t/t3103-ls-tree-misc.sh index d18ba1bd84..81c6343962 100755 --- a/t/t3103-ls-tree-misc.sh +++ b/t/t3103-ls-tree-misc.sh @@ -23,4 +23,19 @@ test_expect_success 'ls-tree fails with non-zero exit code on broken tree' ' test_must_fail git ls-tree -r HEAD ' +for opts in \ + "--long --name-only" \ + "--name-only --name-status" \ + "--name-status --object-only" \ + "--object-only --long" +do + test_expect_success "usage: incompatible options: $opts" ' + test_expect_code 129 git ls-tree $opts $tree + ' + + one_opt=$(echo "$opts" | cut -d' ' -f1) + test_expect_success "usage: incompatible options: $one_opt and --format" ' + test_expect_code 129 git ls-tree $one_opt --format=fmt $tree + ' +done test_done diff --git a/t/t3104-ls-tree-format.sh b/t/t3104-ls-tree-format.sh new file mode 100755 index 0000000000..0769a933d6 --- /dev/null +++ b/t/t3104-ls-tree-format.sh @@ -0,0 +1,76 @@ +#!/bin/sh + +test_description='ls-tree --format' + +TEST_PASSES_SANITIZE_LEAK=true +. ./test-lib.sh + +test_expect_success 'ls-tree --format usage' ' + test_expect_code 129 git ls-tree --format=fmt -l HEAD && + test_expect_code 129 git ls-tree --format=fmt --name-only HEAD && + test_expect_code 129 git ls-tree --format=fmt --name-status HEAD +' + +test_expect_success 'setup' ' + mkdir dir && + test_commit dir/sub-file && + test_commit top-file +' + +test_ls_tree_format () { + format=$1 && + opts=$2 && + fmtopts=$3 && + shift 2 && + + test_expect_success "ls-tree '--format=<$format>' is like options '$opts $fmtopts'" ' + git ls-tree $opts -r HEAD >expect && + git ls-tree --format="$format" -r $fmtopts HEAD >actual && + test_cmp expect actual + ' + + test_expect_success "ls-tree '--format=<$format>' on optimized v.s. non-optimized path" ' + git ls-tree --format="$format" -r $fmtopts HEAD >expect && + git ls-tree --format="> $format" -r $fmtopts HEAD >actual.raw && + sed "s/^> //" >actual <actual.raw && + test_cmp expect actual + ' +} + +test_ls_tree_format \ + "%(objectmode) %(objecttype) %(objectname)%x09%(path)" \ + "" + +test_ls_tree_format \ + "%(objectmode) %(objecttype) %(objectname) %(objectsize:padded)%x09%(path)" \ + "--long" + +test_ls_tree_format \ + "%(path)" \ + "--name-only" + +test_ls_tree_format \ + "%(objectname)" \ + "--object-only" + +test_ls_tree_format \ + "%(objectname)" \ + "--object-only --abbrev" \ + "--abbrev" + +test_ls_tree_format \ + "%(objectmode) %(objecttype) %(objectname)%x09%(path)" \ + "-t" \ + "-t" + +test_ls_tree_format \ + "%(objectmode) %(objecttype) %(objectname)%x09%(path)" \ + "--full-name" \ + "--full-name" + +test_ls_tree_format \ + "%(objectmode) %(objecttype) %(objectname)%x09%(path)" \ + "--full-tree" \ + "--full-tree" + +test_done diff --git a/t/t3400-rebase.sh b/t/t3400-rebase.sh index 71b1735e1d..d5a8ee39fc 100755 --- a/t/t3400-rebase.sh +++ b/t/t3400-rebase.sh @@ -18,10 +18,7 @@ GIT_AUTHOR_EMAIL=bogus@email@address export GIT_AUTHOR_NAME GIT_AUTHOR_EMAIL test_expect_success 'prepare repository with topic branches' ' - git config core.logAllRefUpdates true && - echo First >A && - git update-index --add A && - git commit -m "Add A." && + test_commit "Add A." A First First && git checkout -b force-3way && echo Dummy >Y && git update-index --add Y && @@ -32,9 +29,7 @@ test_expect_success 'prepare repository with topic branches' ' git mv A D/A && git commit -m "Move A." && git checkout -b my-topic-branch main && - echo Second >B && - git update-index --add B && - git commit -m "Add B." && + test_commit "Add B." B Second Second && git checkout -f main && echo Third >>A && git update-index A && @@ -399,6 +394,15 @@ test_expect_success 'switch to branch not checked out' ' git rebase main other ' +test_expect_success 'switch to non-branch detaches HEAD' ' + git checkout main && + old_main=$(git rev-parse HEAD) && + git rebase First Second^0 && + test_cmp_rev HEAD Second && + test_cmp_rev main $old_main && + test_must_fail git symbolic-ref HEAD +' + test_expect_success 'refuse to switch to branch checked out elsewhere' ' git checkout main && git worktree add wt && diff --git a/t/t3404-rebase-interactive.sh b/t/t3404-rebase-interactive.sh index a38f2da769..f31afd4a54 100755 --- a/t/t3404-rebase-interactive.sh +++ b/t/t3404-rebase-interactive.sh @@ -619,9 +619,7 @@ test_expect_success 'rebase a detached HEAD' ' ' test_expect_success 'rebase a commit violating pre-commit' ' - - mkdir -p .git/hooks && - write_script .git/hooks/pre-commit <<-\EOF && + test_hook pre-commit <<-\EOF && test -z "$(git diff --cached --check)" EOF echo "monde! " >> file1 && @@ -636,8 +634,6 @@ test_expect_success 'rebase a commit violating pre-commit' ' ' test_expect_success 'rebase with a file named HEAD in worktree' ' - - rm -fr .git/hooks && git reset --hard && git checkout -b branch3 A && @@ -1688,10 +1684,8 @@ test_expect_success 'valid author header when author contains single quote' ' ' test_expect_success 'post-commit hook is called' ' - test_when_finished "rm -f .git/hooks/post-commit" && >actual && - mkdir -p .git/hooks && - write_script .git/hooks/post-commit <<-\EOS && + test_hook post-commit <<-\EOS && git rev-parse HEAD >>actual EOS ( diff --git a/t/t3412-rebase-root.sh b/t/t3412-rebase-root.sh index 1e9f7833dd..58371d8a54 100755 --- a/t/t3412-rebase-root.sh +++ b/t/t3412-rebase-root.sh @@ -31,12 +31,9 @@ test_expect_success 'rebase --root fails with too many args' ' ' test_expect_success 'setup pre-rebase hook' ' - mkdir -p .git/hooks && - cat >.git/hooks/pre-rebase <<EOF && -#!$SHELL_PATH -echo "\$1,\$2" >.git/PRE-REBASE-INPUT -EOF - chmod +x .git/hooks/pre-rebase + test_hook --setup pre-rebase <<-\EOF + echo "$1,$2" >.git/PRE-REBASE-INPUT + EOF ' cat > expect <<EOF 4 @@ -141,12 +138,9 @@ commit work7~5 EOF test_expect_success 'setup pre-rebase hook that fails' ' - mkdir -p .git/hooks && - cat >.git/hooks/pre-rebase <<EOF && -#!$SHELL_PATH -false -EOF - chmod +x .git/hooks/pre-rebase + test_hook --setup --clobber pre-rebase <<-\EOF + false + EOF ' test_expect_success 'pre-rebase hook stops rebase' ' diff --git a/t/t3413-rebase-hook.sh b/t/t3413-rebase-hook.sh index b4acb3be5c..9fab0d779b 100755 --- a/t/t3413-rebase-hook.sh +++ b/t/t3413-rebase-hook.sh @@ -41,12 +41,9 @@ test_expect_success 'rebase -i' ' ' test_expect_success 'setup pre-rebase hook' ' - mkdir -p .git/hooks && - cat >.git/hooks/pre-rebase <<EOF && -#!$SHELL_PATH -echo "\$1,\$2" >.git/PRE-REBASE-INPUT -EOF - chmod +x .git/hooks/pre-rebase + test_hook --setup pre-rebase <<-\EOF + echo "$1,$2" >.git/PRE-REBASE-INPUT + EOF ' test_expect_success 'pre-rebase hook gets correct input (1)' ' @@ -102,12 +99,9 @@ test_expect_success 'pre-rebase hook gets correct input (6)' ' ' test_expect_success 'setup pre-rebase hook that fails' ' - mkdir -p .git/hooks && - cat >.git/hooks/pre-rebase <<EOF && -#!$SHELL_PATH -false -EOF - chmod +x .git/hooks/pre-rebase + test_hook --setup --clobber pre-rebase <<-\EOF + false + EOF ' test_expect_success 'pre-rebase hook stops rebase (1)' ' diff --git a/t/t3430-rebase-merges.sh b/t/t3430-rebase-merges.sh index 43c82d9a33..f351701fec 100755 --- a/t/t3430-rebase-merges.sh +++ b/t/t3430-rebase-merges.sh @@ -292,9 +292,9 @@ test_expect_success 'post-rewrite hook and fixups work for merges' ' git commit --fixup HEAD same2.t && fixup="$(git rev-parse HEAD)" && - mkdir -p .git/hooks && - test_when_finished "rm .git/hooks/post-rewrite" && - echo "cat >actual" | write_script .git/hooks/post-rewrite && + test_hook post-rewrite <<-\EOF && + cat >actual + EOF test_tick && git rebase -i --autosquash -r HEAD^^^ && diff --git a/t/t3903-stash.sh b/t/t3903-stash.sh index 42638b11d8..4abbc8fcca 100755 --- a/t/t3903-stash.sh +++ b/t/t3903-stash.sh @@ -302,6 +302,18 @@ test_expect_success 'apply -q is quiet' ' test_must_be_empty output.out ' +test_expect_success 'apply --index -q is quiet' ' + # Added file, deleted file, modified file all staged for commit + echo foo >new-file && + echo test >file && + git add new-file file && + git rm other-file && + + git stash && + git stash apply --index -q >output.out 2>&1 && + test_must_be_empty output.out +' + test_expect_success 'save -q is quiet' ' git stash save --quiet >output.out 2>&1 && test_must_be_empty output.out @@ -332,6 +344,27 @@ test_expect_success 'drop -q is quiet' ' test_must_be_empty output.out ' +test_expect_success 'stash push -q --staged refreshes the index' ' + git reset --hard && + echo test >file && + git add file && + git stash push -q --staged && + git diff-files >output.out && + test_must_be_empty output.out +' + +test_expect_success 'stash apply -q --index refreshes the index' ' + echo test >other-file && + git add other-file && + echo another-change >other-file && + git diff-files >expect && + git stash && + + git stash apply -q --index && + git diff-files >actual && + test_cmp expect actual +' + test_expect_success 'stash -k' ' echo bar3 >file && echo bar4 >file2 && diff --git a/t/t4015-diff-whitespace.sh b/t/t4015-diff-whitespace.sh index 9babf13bc9..f3e20dd5bb 100755 --- a/t/t4015-diff-whitespace.sh +++ b/t/t4015-diff-whitespace.sh @@ -6,6 +6,8 @@ test_description='Test special whitespace in diff engine. ' + +TEST_PASSES_SANITIZE_LEAK=true . ./test-lib.sh . "$TEST_DIRECTORY"/lib-diff.sh @@ -1622,7 +1624,7 @@ test_expect_success 'cmd option assumes configured colored-moved' ' test_cmp expected actual ' -test_expect_success 'no effect from --color-moved with --word-diff' ' +test_expect_success 'no effect on diff from --color-moved with --word-diff' ' cat <<-\EOF >text.txt && Lorem Ipsum is simply dummy text of the printing and typesetting industry. EOF @@ -1636,6 +1638,12 @@ test_expect_success 'no effect from --color-moved with --word-diff' ' test_cmp expect actual ' +test_expect_success !SANITIZE_LEAK 'no effect on show from --color-moved with --word-diff' ' + git show --color-moved --word-diff >actual && + git show --word-diff >expect && + test_cmp expect actual +' + test_expect_success 'set up whitespace tests' ' git reset --hard && # Note that these lines have no leading or trailing whitespace. @@ -2016,7 +2024,7 @@ test_expect_success '--color-moved rewinds for MIN_ALNUM_COUNT' ' test_cmp expected actual ' -test_expect_success 'move detection with submodules' ' +test_expect_success !SANITIZE_LEAK 'move detection with submodules' ' test_create_repo bananas && echo ripe >bananas/recipe && git -C bananas add recipe && diff --git a/t/t4018/kotlin-class b/t/t4018/kotlin-class new file mode 100644 index 0000000000..bb864f22e6 --- /dev/null +++ b/t/t4018/kotlin-class @@ -0,0 +1,5 @@ +class RIGHT { + //comment + //comment + return ChangeMe +} diff --git a/t/t4018/kotlin-enum-class b/t/t4018/kotlin-enum-class new file mode 100644 index 0000000000..8885f908fd --- /dev/null +++ b/t/t4018/kotlin-enum-class @@ -0,0 +1,5 @@ +enum class RIGHT{ + // Left + // a comment + ChangeMe +} diff --git a/t/t4018/kotlin-fun b/t/t4018/kotlin-fun new file mode 100644 index 0000000000..2a60280256 --- /dev/null +++ b/t/t4018/kotlin-fun @@ -0,0 +1,5 @@ +fun RIGHT(){ + //a comment + //b comment + return ChangeMe() +} diff --git a/t/t4018/kotlin-inheritace-class b/t/t4018/kotlin-inheritace-class new file mode 100644 index 0000000000..77376c1f05 --- /dev/null +++ b/t/t4018/kotlin-inheritace-class @@ -0,0 +1,5 @@ +open class RIGHT{ + // a comment + // b comment + // ChangeMe +} diff --git a/t/t4018/kotlin-inline-class b/t/t4018/kotlin-inline-class new file mode 100644 index 0000000000..7bf46dd8d4 --- /dev/null +++ b/t/t4018/kotlin-inline-class @@ -0,0 +1,5 @@ +value class RIGHT(Args){ + // a comment + // b comment + ChangeMe +} diff --git a/t/t4018/kotlin-interface b/t/t4018/kotlin-interface new file mode 100644 index 0000000000..f686ba7770 --- /dev/null +++ b/t/t4018/kotlin-interface @@ -0,0 +1,5 @@ +interface RIGHT{ + //another comment + //another comment + //ChangeMe +} diff --git a/t/t4018/kotlin-nested-fun b/t/t4018/kotlin-nested-fun new file mode 100644 index 0000000000..12186858cb --- /dev/null +++ b/t/t4018/kotlin-nested-fun @@ -0,0 +1,9 @@ +class LEFT{ + class CENTER{ + fun RIGHT( a:Int){ + //comment + //comment + ChangeMe + } + } +} diff --git a/t/t4018/kotlin-public-class b/t/t4018/kotlin-public-class new file mode 100644 index 0000000000..9433fcc226 --- /dev/null +++ b/t/t4018/kotlin-public-class @@ -0,0 +1,5 @@ +public class RIGHT{ + //comment1 + //comment2 + ChangeMe +} diff --git a/t/t4018/kotlin-sealed-class b/t/t4018/kotlin-sealed-class new file mode 100644 index 0000000000..0efa4a4eaf --- /dev/null +++ b/t/t4018/kotlin-sealed-class @@ -0,0 +1,5 @@ +sealed class RIGHT { + // a comment + // b comment + ChangeMe +} diff --git a/t/t4034-diff-words.sh b/t/t4034-diff-words.sh index d5abcf4b4c..15764ee9ac 100755 --- a/t/t4034-diff-words.sh +++ b/t/t4034-diff-words.sh @@ -324,6 +324,7 @@ test_language_driver dts test_language_driver fortran test_language_driver html test_language_driver java +test_language_driver kotlin test_language_driver matlab test_language_driver objc test_language_driver pascal diff --git a/t/t4034/kotlin/expect b/t/t4034/kotlin/expect new file mode 100644 index 0000000000..7f76f7540d --- /dev/null +++ b/t/t4034/kotlin/expect @@ -0,0 +1,43 @@ +<BOLD>diff --git a/pre b/post<RESET> +<BOLD>index 11ea3de..2e1df4c 100644<RESET> +<BOLD>--- a/pre<RESET> +<BOLD>+++ b/post<RESET> +<CYAN>@@ -1,30 +1,30 @@<RESET> +println("Hello World<RED>!\n<RESET><GREEN>?<RESET>") +<GREEN>(<RESET>1<GREEN>) (<RESET>-1e10<GREEN>) (<RESET>0xabcdef<GREEN>)<RESET> '<RED>x<RESET><GREEN>y<RESET>' +[<RED>a<RESET><GREEN>x<RESET>] <RED>a<RESET><GREEN>x<RESET>-><RED>b a<RESET><GREEN>y x<RESET>.<RED>b<RESET><GREEN>y<RESET> +!<RED>a a<RESET><GREEN>x x<RESET>.inv() <RED>a<RESET><GREEN>x<RESET>*<RED>b a<RESET><GREEN>y x<RESET>&<RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET>*<RED>b a<RESET><GREEN>y x<RESET>/<RED>b a<RESET><GREEN>y x<RESET>%<RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET>+<RED>b a<RESET><GREEN>y x<RESET>-<RED>b<RESET><GREEN>y<RESET> +a <RED>shr<RESET><GREEN>shl<RESET> b +<RED>a<RESET><GREEN>x<RESET><<RED>b a<RESET><GREEN>y x<RESET><=<RED>b a<RESET><GREEN>y x<RESET>><RED>b a<RESET><GREEN>y x<RESET>>=<RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET>==<RED>b a<RESET><GREEN>y x<RESET>!=<RED>b a<RESET><GREEN>y x<RESET>===<RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET> and <RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET>^<RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET> or <RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET>&&<RED>b a<RESET><GREEN>y x<RESET>||<RED>b<RESET> +<RED>a<RESET><GREEN>y<RESET> +<GREEN>x<RESET>=<RED>b a<RESET><GREEN>y x<RESET>+=<RED>b a<RESET><GREEN>y x<RESET>-=<RED>b a<RESET><GREEN>y x<RESET>*=<RED>b a<RESET><GREEN>y x<RESET>/=<RED>b a<RESET><GREEN>y x<RESET>%=<RED>b a<RESET><GREEN>y x<RESET><<=<RED>b a<RESET><GREEN>y x<RESET>>>=<RED>b a<RESET><GREEN>y x<RESET>&=<RED>b a<RESET><GREEN>y x<RESET>^=<RED>b a<RESET><GREEN>y x<RESET>|=<RED>b<RESET><GREEN>y<RESET> +a<RED>=<RESET><GREEN>+=<RESET>b c<RED>+=<RESET><GREEN>=<RESET>d e<RED>-=<RESET><GREEN><=<RESET>f g<RED>*=<RESET><GREEN>>=<RESET>h i<RED>/=<RESET><GREEN>/<RESET>j k<RED>%=<RESET><GREEN>%<RESET>l m<RED><<=<RESET><GREEN><<<RESET>n o<RED>>>=<RESET><GREEN>>><RESET>p q<RED>&=<RESET><GREEN>&<RESET>r s<RED>^=<RESET><GREEN>^<RESET>t u<RED>|=<RESET><GREEN>|<RESET>v +a<RED><<=<RESET><GREEN><=<RESET>b +a<RED>||<RESET><GREEN>|<RESET>b a<RED>&&<RESET><GREEN>&<RESET>b +<RED>a<RESET><GREEN>x<RESET>,y +--a<RED>==<RESET><GREEN>!=<RESET>--b +a++<RED>==<RESET><GREEN>!=<RESET>++b +<RED>0xFF_EC_DE_5E 0b100_000 100_000<RESET><GREEN>0xFF_E1_DE_5E 0b100_100 200_000<RESET> +a<RED>==<RESET><GREEN>===<RESET>b +a<RED>!!<RESET><GREEN>!=<RESET>b +<RED>_32<RESET><GREEN>_33<RESET>.find(arr) +X.<RED>fill<RESET><GREEN>find<RESET>() +X.<RED>u<RESET><GREEN>f<RESET>+1 +X.u<RED>-<RESET><GREEN>+<RESET>2 +a<RED>.<RESET><GREEN>..<RESET>b +a<RED>?.<RESET><GREEN>?:<RESET>b +<RED>.32_00_456<RESET><GREEN>.32_00_446<RESET> diff --git a/t/t4034/kotlin/post b/t/t4034/kotlin/post new file mode 100644 index 0000000000..2e1df4c6d5 --- /dev/null +++ b/t/t4034/kotlin/post @@ -0,0 +1,30 @@ +println("Hello World?") +(1) (-1e10) (0xabcdef) 'y' +[x] x->y x.y +!x x.inv() x*y x&y +x*y x/y x%y +x+y x-y +a shl b +x<y x<=y x>y x>=y +x==y x!=y x===y +x and y +x^y +x or y +x&&y x||y +x=y x+=y x-=y x*=y x/=y x%=y x<<=y x>>=y x&=y x^=y x|=y +a+=b c=d e<=f g>=h i/j k%l m<<n o>>p q&r s^t u|v +a<=b +a|b a&b +x,y +--a!=--b +a++!=++b +0xFF_E1_DE_5E 0b100_100 200_000 +a===b +a!=b +_33.find(arr) +X.find() +X.f+1 +X.u+2 +a..b +a?:b +.32_00_446 diff --git a/t/t4034/kotlin/pre b/t/t4034/kotlin/pre new file mode 100644 index 0000000000..11ea3de665 --- /dev/null +++ b/t/t4034/kotlin/pre @@ -0,0 +1,30 @@ +println("Hello World!\n") +1 -1e10 0xabcdef 'x' +[a] a->b a.b +!a a.inv() a*b a&b +a*b a/b a%b +a+b a-b +a shr b +a<b a<=b a>b a>=b +a==b a!=b a===b +a and b +a^b +a or b +a&&b a||b +a=b a+=b a-=b a*=b a/=b a%=b a<<=b a>>=b a&=b a^=b a|=b +a=b c+=d e-=f g*=h i/=j k%=l m<<=n o>>=p q&=r s^=t u|=v +a<<=b +a||b a&&b +a,y +--a==--b +a++==++b +0xFF_EC_DE_5E 0b100_000 100_000 +a==b +a!!b +_32.find(arr) +X.fill() +X.u+1 +X.u-2 +a.b +a?.b +.32_00_456 diff --git a/t/t4150-am.sh b/t/t4150-am.sh index 159fae8d01..cdad4b6880 100755 --- a/t/t4150-am.sh +++ b/t/t4150-am.sh @@ -315,12 +315,10 @@ test_expect_success 'am --patch-format=hg applies hg patch' ' ' test_expect_success 'am with applypatch-msg hook' ' - test_when_finished "rm -f .git/hooks/applypatch-msg" && rm -fr .git/rebase-apply && git reset --hard && git checkout first && - mkdir -p .git/hooks && - write_script .git/hooks/applypatch-msg <<-\EOF && + test_hook applypatch-msg <<-\EOF && cat "$1" >actual-msg && echo hook-message >"$1" EOF @@ -335,12 +333,10 @@ test_expect_success 'am with applypatch-msg hook' ' ' test_expect_success 'am with failing applypatch-msg hook' ' - test_when_finished "rm -f .git/hooks/applypatch-msg" && rm -fr .git/rebase-apply && git reset --hard && git checkout first && - mkdir -p .git/hooks && - write_script .git/hooks/applypatch-msg <<-\EOF && + test_hook applypatch-msg <<-\EOF && exit 1 EOF test_must_fail git am patch1 && @@ -350,12 +346,10 @@ test_expect_success 'am with failing applypatch-msg hook' ' ' test_expect_success 'am with pre-applypatch hook' ' - test_when_finished "rm -f .git/hooks/pre-applypatch" && rm -fr .git/rebase-apply && git reset --hard && git checkout first && - mkdir -p .git/hooks && - write_script .git/hooks/pre-applypatch <<-\EOF && + test_hook pre-applypatch <<-\EOF && git diff first >diff.actual exit 0 EOF @@ -368,12 +362,10 @@ test_expect_success 'am with pre-applypatch hook' ' ' test_expect_success 'am with failing pre-applypatch hook' ' - test_when_finished "rm -f .git/hooks/pre-applypatch" && rm -fr .git/rebase-apply && git reset --hard && git checkout first && - mkdir -p .git/hooks && - write_script .git/hooks/pre-applypatch <<-\EOF && + test_hook pre-applypatch <<-\EOF && exit 1 EOF test_must_fail git am patch1 && @@ -383,12 +375,10 @@ test_expect_success 'am with failing pre-applypatch hook' ' ' test_expect_success 'am with post-applypatch hook' ' - test_when_finished "rm -f .git/hooks/post-applypatch" && rm -fr .git/rebase-apply && git reset --hard && git checkout first && - mkdir -p .git/hooks && - write_script .git/hooks/post-applypatch <<-\EOF && + test_hook post-applypatch <<-\EOF && git rev-parse HEAD >head.actual git diff second >diff.actual exit 0 @@ -403,12 +393,10 @@ test_expect_success 'am with post-applypatch hook' ' ' test_expect_success 'am with failing post-applypatch hook' ' - test_when_finished "rm -f .git/hooks/post-applypatch" && rm -fr .git/rebase-apply && git reset --hard && git checkout first && - mkdir -p .git/hooks && - write_script .git/hooks/post-applypatch <<-\EOF && + test_hook post-applypatch <<-\EOF && git rev-parse HEAD >head.actual exit 1 EOF diff --git a/t/t5401-update-hooks.sh b/t/t5401-update-hooks.sh index 6012cc8172..001b7a17ad 100755 --- a/t/t5401-update-hooks.sh +++ b/t/t5401-update-hooks.sh @@ -20,45 +20,37 @@ test_expect_success setup ' git clone --bare ./. victim.git && GIT_DIR=victim.git git update-ref refs/heads/tofail $commit1 && git update-ref refs/heads/main $commit1 && - git update-ref refs/heads/tofail $commit0 -' + git update-ref refs/heads/tofail $commit0 && -cat >victim.git/hooks/pre-receive <<'EOF' -#!/bin/sh -printf %s "$@" >>$GIT_DIR/pre-receive.args -cat - >$GIT_DIR/pre-receive.stdin -echo STDOUT pre-receive -echo STDERR pre-receive >&2 -EOF -chmod u+x victim.git/hooks/pre-receive + test_hook --setup -C victim.git pre-receive <<-\EOF && + printf %s "$@" >>$GIT_DIR/pre-receive.args + cat - >$GIT_DIR/pre-receive.stdin + echo STDOUT pre-receive + echo STDERR pre-receive >&2 + EOF -cat >victim.git/hooks/update <<'EOF' -#!/bin/sh -echo "$@" >>$GIT_DIR/update.args -read x; printf %s "$x" >$GIT_DIR/update.stdin -echo STDOUT update $1 -echo STDERR update $1 >&2 -test "$1" = refs/heads/main || exit -EOF -chmod u+x victim.git/hooks/update + test_hook --setup -C victim.git update <<-\EOF && + echo "$@" >>$GIT_DIR/update.args + read x; printf %s "$x" >$GIT_DIR/update.stdin + echo STDOUT update $1 + echo STDERR update $1 >&2 + test "$1" = refs/heads/main || exit + EOF -cat >victim.git/hooks/post-receive <<'EOF' -#!/bin/sh -printf %s "$@" >>$GIT_DIR/post-receive.args -cat - >$GIT_DIR/post-receive.stdin -echo STDOUT post-receive -echo STDERR post-receive >&2 -EOF -chmod u+x victim.git/hooks/post-receive + test_hook --setup -C victim.git post-receive <<-\EOF && + printf %s "$@" >>$GIT_DIR/post-receive.args + cat - >$GIT_DIR/post-receive.stdin + echo STDOUT post-receive + echo STDERR post-receive >&2 + EOF -cat >victim.git/hooks/post-update <<'EOF' -#!/bin/sh -echo "$@" >>$GIT_DIR/post-update.args -read x; printf %s "$x" >$GIT_DIR/post-update.stdin -echo STDOUT post-update -echo STDERR post-update >&2 -EOF -chmod u+x victim.git/hooks/post-update + test_hook --setup -C victim.git post-update <<-\EOF + echo "$@" >>$GIT_DIR/post-update.args + read x; printf %s "$x" >$GIT_DIR/post-update.stdin + echo STDOUT post-update + echo STDERR post-update >&2 + EOF +' test_expect_success push ' test_must_fail git send-pack --force ./victim.git \ @@ -136,7 +128,7 @@ test_expect_success 'send-pack stderr contains hook messages' ' ' test_expect_success 'pre-receive hook that forgets to read its input' ' - write_script victim.git/hooks/pre-receive <<-\EOF && + test_hook --clobber -C victim.git pre-receive <<-\EOF && exit 0 EOF rm -f victim.git/hooks/update victim.git/hooks/post-update && diff --git a/t/t5402-post-merge-hook.sh b/t/t5402-post-merge-hook.sh index 3e5e19c719..915af2de95 100755 --- a/t/t5402-post-merge-hook.sh +++ b/t/t5402-post-merge-hook.sh @@ -25,13 +25,15 @@ test_expect_success setup ' GIT_DIR=clone2/.git git update-index --add a ' -for clone in 1 2; do - cat >clone${clone}/.git/hooks/post-merge <<'EOF' -#!/bin/sh -echo $@ >> $GIT_DIR/post-merge.args -EOF - chmod u+x clone${clone}/.git/hooks/post-merge -done +test_expect_success 'setup clone hooks' ' + test_when_finished "rm -f hook" && + cat >hook <<-\EOF && + echo $@ >>$GIT_DIR/post-merge.args + EOF + + test_hook --setup -C clone1 post-merge <hook && + test_hook --setup -C clone2 post-merge <hook +' test_expect_success 'post-merge does not run for up-to-date ' ' GIT_DIR=clone1/.git git merge $commit0 && diff --git a/t/t5403-post-checkout-hook.sh b/t/t5403-post-checkout-hook.sh index d118181690..978f240cda 100755 --- a/t/t5403-post-checkout-hook.sh +++ b/t/t5403-post-checkout-hook.sh @@ -10,8 +10,7 @@ export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME . ./test-lib.sh test_expect_success setup ' - mkdir -p .git/hooks && - write_script .git/hooks/post-checkout <<-\EOF && + test_hook --setup post-checkout <<-\EOF && echo "$@" >.git/post-checkout.args EOF test_commit one && diff --git a/t/t5406-remote-rejects.sh b/t/t5406-remote-rejects.sh index 5c509db6fc..dcbeb42082 100755 --- a/t/t5406-remote-rejects.sh +++ b/t/t5406-remote-rejects.sh @@ -5,7 +5,7 @@ test_description='remote push rejects are reported by client' . ./test-lib.sh test_expect_success 'setup' ' - write_script .git/hooks/update <<-\EOF && + test_hook update <<-\EOF && exit 1 EOF echo 1 >file && diff --git a/t/t5407-post-rewrite-hook.sh b/t/t5407-post-rewrite-hook.sh index 6da8d760e2..5f3ff051ca 100755 --- a/t/t5407-post-rewrite-hook.sh +++ b/t/t5407-post-rewrite-hook.sh @@ -17,15 +17,13 @@ test_expect_success 'setup' ' git checkout A^0 && test_commit E bar E && test_commit F foo F && - git checkout main -' + git checkout main && -cat >.git/hooks/post-rewrite <<EOF -#!/bin/sh -echo \$@ > "$TRASH_DIRECTORY"/post-rewrite.args -cat > "$TRASH_DIRECTORY"/post-rewrite.data -EOF -chmod u+x .git/hooks/post-rewrite + test_hook --setup post-rewrite <<-EOF + echo \$@ > "$TRASH_DIRECTORY"/post-rewrite.args + cat > "$TRASH_DIRECTORY"/post-rewrite.data + EOF +' clear_hook_input () { rm -f post-rewrite.args post-rewrite.data diff --git a/t/t5409-colorize-remote-messages.sh b/t/t5409-colorize-remote-messages.sh index 9f1a483f42..fa5de4500a 100755 --- a/t/t5409-colorize-remote-messages.sh +++ b/t/t5409-colorize-remote-messages.sh @@ -5,7 +5,7 @@ test_description='remote messages are colorized on the client' . ./test-lib.sh test_expect_success 'setup' ' - write_script .git/hooks/update <<-\EOF && + test_hook --setup update <<-\EOF && echo error: error echo ERROR: also highlighted echo hint: hint diff --git a/t/t5411-proc-receive-hook.sh b/t/t5411-proc-receive-hook.sh index 98b0e81208..92cf52c6d4 100755 --- a/t/t5411-proc-receive-hook.sh +++ b/t/t5411-proc-receive-hook.sh @@ -36,7 +36,7 @@ setup_upstream_and_workbench () { TAG=$(git -C workbench rev-parse v123) && # setup pre-receive hook - write_script upstream.git/hooks/pre-receive <<-\EOF && + test_hook --setup -C upstream.git pre-receive <<-\EOF && exec >&2 echo "# pre-receive hook" while read old new ref @@ -46,7 +46,7 @@ setup_upstream_and_workbench () { EOF # setup post-receive hook - write_script upstream.git/hooks/post-receive <<-\EOF && + test_hook --setup -C upstream.git post-receive <<-\EOF && exec >&2 echo "# post-receive hook" while read old new ref diff --git a/t/t5411/once-0010-report-status-v1.sh b/t/t5411/once-0010-report-status-v1.sh index 297b10925d..f9ffb01e50 100644 --- a/t/t5411/once-0010-report-status-v1.sh +++ b/t/t5411/once-0010-report-status-v1.sh @@ -3,7 +3,7 @@ test_expect_success "setup receive.procReceiveRefs" ' ' test_expect_success "setup proc-receive hook" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic1" \ diff --git a/t/t5411/test-0002-pre-receive-declined.sh b/t/t5411/test-0002-pre-receive-declined.sh index 0c3490c9b1..98a9d13041 100644 --- a/t/t5411/test-0002-pre-receive-declined.sh +++ b/t/t5411/test-0002-pre-receive-declined.sh @@ -1,6 +1,6 @@ test_expect_success "setup pre-receive hook ($PROTOCOL)" ' mv "$upstream/hooks/pre-receive" "$upstream/hooks/pre-receive.ok" && - write_script "$upstream/hooks/pre-receive" <<-EOF + test_hook -C "$upstream" --clobber pre-receive <<-\EOF exit 1 EOF ' @@ -21,7 +21,7 @@ test_expect_success "git-push is declined ($PROTOCOL)" ' EOF test_cmp expect actual && - test_cmp_refs -C "$upstream" <<-EOF + test_cmp_refs -C "$upstream" <<-\EOF <COMMIT-A> refs/heads/main EOF ' diff --git a/t/t5411/test-0003-pre-receive-declined--porcelain.sh b/t/t5411/test-0003-pre-receive-declined--porcelain.sh index 2393b04ad9..67ca6dc4f8 100644 --- a/t/t5411/test-0003-pre-receive-declined--porcelain.sh +++ b/t/t5411/test-0003-pre-receive-declined--porcelain.sh @@ -1,6 +1,6 @@ test_expect_success "setup pre-receive hook ($PROTOCOL/porcelain)" ' mv "$upstream/hooks/pre-receive" "$upstream/hooks/pre-receive.ok" && - write_script "$upstream/hooks/pre-receive" <<-EOF + test_hook -C "$upstream" --clobber pre-receive <<-\EOF exit 1 EOF ' diff --git a/t/t5411/test-0013-bad-protocol.sh b/t/t5411/test-0013-bad-protocol.sh index c08a00ded2..8d22e17aee 100644 --- a/t/t5411/test-0013-bad-protocol.sh +++ b/t/t5411/test-0013-bad-protocol.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (unknown version, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --version 2 EOF @@ -40,7 +40,7 @@ test_expect_success "proc-receive: bad protocol (unknown version, $PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (hook --die-read-version, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-read-version EOF @@ -65,13 +65,13 @@ test_expect_success "proc-receive: bad protocol (hook --die-read-version, $PROTO grep "remote: fatal: die with the --die-read-version option" out-$test_count && grep "remote: error: fail to negotiate version with proc-receive hook" out-$test_count && - test_cmp_refs -C "$upstream" <<-EOF + test_cmp_refs -C "$upstream" <<-\EOF <COMMIT-A> refs/heads/main EOF ' test_expect_success "setup proc-receive hook (hook --die-write-version, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-write-version EOF @@ -102,7 +102,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-write-version, $PROT ' test_expect_success "setup proc-receive hook (hook --die-read-commands, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-read-commands EOF @@ -132,7 +132,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-read-commands, $PROT ' test_expect_success "setup proc-receive hook (hook --die-read-push-options, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-read-push-options EOF @@ -164,7 +164,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-read-push-options, $ ' test_expect_success "setup proc-receive hook (hook --die-write-report, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-write-report EOF @@ -194,7 +194,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-write-report, $PROTO ' test_expect_success "setup proc-receive hook (no report, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v EOF @@ -236,7 +236,7 @@ test_expect_success "cleanup ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (no ref, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok" @@ -269,7 +269,7 @@ test_expect_success "proc-receive: bad protocol (no ref, $PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (unknown status, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "xx refs/for/main/topic" diff --git a/t/t5411/test-0014-bad-protocol--porcelain.sh b/t/t5411/test-0014-bad-protocol--porcelain.sh index 3eaa597e0f..298a3d1fec 100644 --- a/t/t5411/test-0014-bad-protocol--porcelain.sh +++ b/t/t5411/test-0014-bad-protocol--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (unknown version, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --version 2 EOF @@ -40,7 +40,7 @@ test_expect_success "proc-receive: bad protocol (unknown version, $PROTOCOL/porc ' test_expect_success "setup proc-receive hook (hook --die-read-version, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-read-version EOF @@ -71,7 +71,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-read-version, $PROTO ' test_expect_success "setup proc-receive hook (hook --die-write-version, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-write-version EOF @@ -102,7 +102,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-write-version, $PROT ' test_expect_success "setup proc-receive hook (hook --die-read-commands, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-read-commands EOF @@ -132,7 +132,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-read-commands, $PROT ' test_expect_success "setup proc-receive hook (hook --die-read-push-options, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-read-push-options EOF @@ -164,7 +164,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-read-push-options, $ ' test_expect_success "setup proc-receive hook (hook --die-write-report, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v --die-write-report EOF @@ -194,7 +194,7 @@ test_expect_success "proc-receive: bad protocol (hook --die-write-report, $PROTO ' test_expect_success "setup proc-receive hook (no report, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v EOF @@ -236,7 +236,7 @@ test_expect_success "cleanup ($PROTOCOL/porcelain)" ' ' test_expect_success "setup proc-receive hook (no ref, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok" @@ -270,7 +270,7 @@ test_expect_success "proc-receive: bad protocol (no ref, $PROTOCOL/porcelain)" ' ' test_expect_success "setup proc-receive hook (unknown status, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "xx refs/for/main/topic" diff --git a/t/t5411/test-0020-report-ng.sh b/t/t5411/test-0020-report-ng.sh index e915dbc28d..6347c9629b 100644 --- a/t/t5411/test-0020-report-ng.sh +++ b/t/t5411/test-0020-report-ng.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (ng, no message, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ng refs/for/main/topic" @@ -31,7 +31,7 @@ test_expect_success "proc-receive: fail to update (ng, no message, $PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (ng message, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ng refs/for/main/topic error msg" diff --git a/t/t5411/test-0021-report-ng--porcelain.sh b/t/t5411/test-0021-report-ng--porcelain.sh index 2a392e099b..502b34fe3d 100644 --- a/t/t5411/test-0021-report-ng--porcelain.sh +++ b/t/t5411/test-0021-report-ng--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (ng, no message, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ng refs/for/main/topic" @@ -32,7 +32,7 @@ test_expect_success "proc-receive: fail to update (ng, no message, $PROTOCOL/por ' test_expect_success "setup proc-receive hook (ng message, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ng refs/for/main/topic error msg" diff --git a/t/t5411/test-0022-report-unexpect-ref.sh b/t/t5411/test-0022-report-unexpect-ref.sh index f7a494bdb9..7744392a62 100644 --- a/t/t5411/test-0022-report-unexpect-ref.sh +++ b/t/t5411/test-0022-report-unexpect-ref.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (unexpected ref, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/heads/main" diff --git a/t/t5411/test-0023-report-unexpect-ref--porcelain.sh b/t/t5411/test-0023-report-unexpect-ref--porcelain.sh index 63c479e975..6d116ef692 100644 --- a/t/t5411/test-0023-report-unexpect-ref--porcelain.sh +++ b/t/t5411/test-0023-report-unexpect-ref--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (unexpected ref, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/heads/main" diff --git a/t/t5411/test-0024-report-unknown-ref.sh b/t/t5411/test-0024-report-unknown-ref.sh index af055aa086..619ca2f421 100644 --- a/t/t5411/test-0024-report-unknown-ref.sh +++ b/t/t5411/test-0024-report-unknown-ref.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (unexpected ref, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" diff --git a/t/t5411/test-0025-report-unknown-ref--porcelain.sh b/t/t5411/test-0025-report-unknown-ref--porcelain.sh index 99601ca321..8b3f5d05a3 100644 --- a/t/t5411/test-0025-report-unknown-ref--porcelain.sh +++ b/t/t5411/test-0025-report-unknown-ref--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (unexpected ref, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" diff --git a/t/t5411/test-0026-push-options.sh b/t/t5411/test-0026-push-options.sh index fec5f95793..6dfc7b1c0d 100644 --- a/t/t5411/test-0026-push-options.sh +++ b/t/t5411/test-0026-push-options.sh @@ -1,6 +1,6 @@ test_expect_success "setup proc-receive hook and disable push-options ($PROTOCOL)" ' git -C "$upstream" config receive.advertisePushOptions false && - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" @@ -31,7 +31,7 @@ test_expect_success "enable push options ($PROTOCOL)" ' ' test_expect_success "setup version=0 for proc-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ --version 0 \ @@ -75,7 +75,7 @@ test_expect_success "proc-receive: ignore push-options for version 0 ($PROTOCOL) ' test_expect_success "restore proc-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" diff --git a/t/t5411/test-0027-push-options--porcelain.sh b/t/t5411/test-0027-push-options--porcelain.sh index 8fb75a8789..768880b40f 100644 --- a/t/t5411/test-0027-push-options--porcelain.sh +++ b/t/t5411/test-0027-push-options--porcelain.sh @@ -1,6 +1,6 @@ test_expect_success "setup proc-receive hook and disable push-options ($PROTOCOL/porcelain)" ' git -C "$upstream" config receive.advertisePushOptions false && - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" @@ -32,7 +32,7 @@ test_expect_success "enable push options ($PROTOCOL/porcelain)" ' ' test_expect_success "setup version=0 for proc-receive hook ($PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ --version 0 \ @@ -78,7 +78,7 @@ test_expect_success "proc-receive: ignore push-options for version 0 ($PROTOCOL/ ' test_expect_success "restore proc-receive hook ($PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" diff --git a/t/t5411/test-0030-report-ok.sh b/t/t5411/test-0030-report-ok.sh index a3a6278213..0f190a6e85 100644 --- a/t/t5411/test-0030-report-ok.sh +++ b/t/t5411/test-0030-report-ok.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (ok, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" diff --git a/t/t5411/test-0031-report-ok--porcelain.sh b/t/t5411/test-0031-report-ok--porcelain.sh index 0e175388b6..7ec3981263 100644 --- a/t/t5411/test-0031-report-ok--porcelain.sh +++ b/t/t5411/test-0031-report-ok--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (ok, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" diff --git a/t/t5411/test-0032-report-with-options.sh b/t/t5411/test-0032-report-with-options.sh index 988a4302a6..07733b94b8 100644 --- a/t/t5411/test-0032-report-with-options.sh +++ b/t/t5411/test-0032-report-with-options.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (option without matching ok, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "option refname refs/pull/123/head" \ @@ -30,7 +30,7 @@ test_expect_success "proc-receive: report option without matching ok ($PROTOCOL) ' test_expect_success "setup proc-receive hook (option refname, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -62,7 +62,7 @@ test_expect_success "proc-receive: report option refname ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (option refname and forced-update, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -95,7 +95,7 @@ test_expect_success "proc-receive: report option refname and forced-update ($PRO ' test_expect_success "setup proc-receive hook (option refname and old-oid, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -129,7 +129,7 @@ test_expect_success "proc-receive: report option refname and old-oid ($PROTOCOL) ' test_expect_success "setup proc-receive hook (option old-oid, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -161,7 +161,7 @@ test_expect_success "proc-receive: report option old-oid ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (option old-oid and new-oid, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -195,7 +195,7 @@ test_expect_success "proc-receive: report option old-oid and new-oid ($PROTOCOL) ' test_expect_success "setup proc-receive hook (report with multiple rewrites, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/a/b/c/topic" \ diff --git a/t/t5411/test-0033-report-with-options--porcelain.sh b/t/t5411/test-0033-report-with-options--porcelain.sh index daacb3d69d..2e1831b104 100644 --- a/t/t5411/test-0033-report-with-options--porcelain.sh +++ b/t/t5411/test-0033-report-with-options--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (option without matching ok, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "option refname refs/pull/123/head" \ @@ -31,7 +31,7 @@ test_expect_success "proc-receive: report option without matching ok ($PROTOCOL/ ' test_expect_success "setup proc-receive hook (option refname, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -64,7 +64,7 @@ test_expect_success "proc-receive: report option refname ($PROTOCOL/porcelain)" ' test_expect_success "setup proc-receive hook (option refname and forced-update, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -99,7 +99,7 @@ test_expect_success "proc-receive: report option refname and forced-update ($PRO ' test_expect_success "setup proc-receive hook (option refname and old-oid, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -134,7 +134,7 @@ test_expect_success "proc-receive: report option refname and old-oid ($PROTOCOL/ ' test_expect_success "setup proc-receive hook (option old-oid, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -167,7 +167,7 @@ test_expect_success "proc-receive: report option old-oid ($PROTOCOL/porcelain)" ' test_expect_success "setup proc-receive hook (option old-oid and new-oid, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -202,7 +202,7 @@ test_expect_success "proc-receive: report option old-oid and new-oid ($PROTOCOL/ ' test_expect_success "setup proc-receive hook (report with multiple rewrites, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/a/b/c/topic" \ diff --git a/t/t5411/test-0034-report-ft.sh b/t/t5411/test-0034-report-ft.sh index 73a47d1ffd..0e37535065 100644 --- a/t/t5411/test-0034-report-ft.sh +++ b/t/t5411/test-0034-report-ft.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (ft, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ diff --git a/t/t5411/test-0035-report-ft--porcelain.sh b/t/t5411/test-0035-report-ft--porcelain.sh index c350201107..b9a05181f1 100644 --- a/t/t5411/test-0035-report-ft--porcelain.sh +++ b/t/t5411/test-0035-report-ft--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (fall-through, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-\EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ diff --git a/t/t5411/test-0036-report-multi-rewrite-for-one-ref.sh b/t/t5411/test-0036-report-multi-rewrite-for-one-ref.sh index 8c8a6c16e1..889e97057b 100644 --- a/t/t5411/test-0036-report-multi-rewrite-for-one-ref.sh +++ b/t/t5411/test-0036-report-multi-rewrite-for-one-ref.sh @@ -14,7 +14,7 @@ test_expect_success "setup git config for remote-tracking of special refs" ' ' test_expect_success "setup proc-receive hook (multiple rewrites for one ref, no refname for the 1st rewrite, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -87,7 +87,7 @@ test_expect_success "proc-receive: check remote-tracking #1 ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (multiple rewrites for one ref, no refname for the 2nd rewrite, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -162,7 +162,7 @@ test_expect_success "proc-receive: check remote-tracking #2 ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook (multiple rewrites for one ref, $PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ diff --git a/t/t5411/test-0037-report-multi-rewrite-for-one-ref--porcelain.sh b/t/t5411/test-0037-report-multi-rewrite-for-one-ref--porcelain.sh index bc44810f33..1e523b1c17 100644 --- a/t/t5411/test-0037-report-multi-rewrite-for-one-ref--porcelain.sh +++ b/t/t5411/test-0037-report-multi-rewrite-for-one-ref--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook (multiple rewrites for one ref, no refname for the 1st rewrite, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -58,7 +58,7 @@ test_expect_success "proc-receive: multiple rewrite for one ref, no refname for ' test_expect_success "setup proc-receive hook (multiple rewrites for one ref, no refname for the 2nd rewrite, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ @@ -119,7 +119,7 @@ test_expect_success "proc-receive: multiple rewrites for one ref, no refname for ' test_expect_success "setup proc-receive hook (multiple rewrites for one ref, $PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/main/topic" \ diff --git a/t/t5411/test-0038-report-mixed-refs.sh b/t/t5411/test-0038-report-mixed-refs.sh index e63fe7ba11..4c70e84e41 100644 --- a/t/t5411/test-0038-report-mixed-refs.sh +++ b/t/t5411/test-0038-report-mixed-refs.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/next/topic2" \ diff --git a/t/t5411/test-0039-report-mixed-refs--porcelain.sh b/t/t5411/test-0039-report-mixed-refs--porcelain.sh index 99d17b73af..40f4c5b1af 100644 --- a/t/t5411/test-0039-report-mixed-refs--porcelain.sh +++ b/t/t5411/test-0039-report-mixed-refs--porcelain.sh @@ -1,5 +1,5 @@ test_expect_success "setup proc-receive hook ($PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/for/next/topic2" \ diff --git a/t/t5411/test-0040-process-all-refs.sh b/t/t5411/test-0040-process-all-refs.sh index 2f405adefa..7ae3851efb 100644 --- a/t/t5411/test-0040-process-all-refs.sh +++ b/t/t5411/test-0040-process-all-refs.sh @@ -17,7 +17,7 @@ test_expect_success "setup upstream branches ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/heads/main" \ diff --git a/t/t5411/test-0041-process-all-refs--porcelain.sh b/t/t5411/test-0041-process-all-refs--porcelain.sh index c88405792e..02e1e084d6 100644 --- a/t/t5411/test-0041-process-all-refs--porcelain.sh +++ b/t/t5411/test-0041-process-all-refs--porcelain.sh @@ -17,7 +17,7 @@ test_expect_success "setup upstream branches ($PROTOCOL/porcelain)" ' ' test_expect_success "setup proc-receive hook ($PROTOCOL/porcelain)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/heads/main" \ diff --git a/t/t5411/test-0050-proc-receive-refs-with-modifiers.sh b/t/t5411/test-0050-proc-receive-refs-with-modifiers.sh index 31989f0185..7efdfe5598 100644 --- a/t/t5411/test-0050-proc-receive-refs-with-modifiers.sh +++ b/t/t5411/test-0050-proc-receive-refs-with-modifiers.sh @@ -9,7 +9,7 @@ test_expect_success "config receive.procReceiveRefs with modifiers ($PROTOCOL)" ' test_expect_success "setup proc-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/heads/main" \ @@ -70,7 +70,7 @@ test_expect_success "setup upstream: create tags/v123 ($PROTOCOL)" ' ' test_expect_success "setup proc-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/proc-receive" <<-EOF + test_hook -C "$upstream" --clobber proc-receive <<-EOF printf >&2 "# proc-receive hook\n" test-tool proc-receive -v \ -r "ok refs/heads/main" \ diff --git a/t/t5503-tagfollow.sh b/t/t5503-tagfollow.sh index a3c01014b7..acdb731edf 100755 --- a/t/t5503-tagfollow.sh +++ b/t/t5503-tagfollow.sh @@ -169,7 +169,7 @@ test_expect_success 'atomic fetch with failing backfill' ' # one of both fails to update correctly. # # To trigger failure we simply abort when backfilling a tag. - write_script clone3/.git/hooks/reference-transaction <<-\EOF && + test_hook -C clone3 reference-transaction <<-\EOF && while read oldrev newrev reference do if test "$reference" = refs/tags/tag1 @@ -201,7 +201,7 @@ test_expect_success 'atomic fetch with backfill should use single transaction' ' $ZERO_OID $T refs/tags/tag1 EOF - write_script clone4/.git/hooks/reference-transaction <<-\EOF && + test_hook -C clone4 reference-transaction <<-\EOF && ( echo "$*" && cat ) >>actual EOF diff --git a/t/t5510-fetch.sh b/t/t5510-fetch.sh index 48e14e2dab..6f38a69fbb 100755 --- a/t/t5510-fetch.sh +++ b/t/t5510-fetch.sh @@ -273,7 +273,7 @@ test_expect_success 'fetch --atomic executes a single reference transaction only EOF rm -f atomic/actual && - write_script atomic/.git/hooks/reference-transaction <<-\EOF && + test_hook -C atomic reference-transaction <<-\EOF && ( echo "$*" && cat ) >>actual EOF @@ -306,7 +306,7 @@ test_expect_success 'fetch --atomic aborts all reference updates if hook aborts' EOF rm -f atomic/actual && - write_script atomic/.git/hooks/reference-transaction <<-\EOF && + test_hook -C atomic/.git reference-transaction <<-\EOF && ( echo "$*" && cat ) >>actual exit 1 EOF @@ -334,7 +334,7 @@ test_expect_success 'fetch --atomic --append appends to FETCH_HEAD' ' test_line_count = 2 atomic/.git/FETCH_HEAD && cp atomic/.git/FETCH_HEAD expected && - write_script atomic/.git/hooks/reference-transaction <<-\EOF && + test_hook -C atomic reference-transaction <<-\EOF && exit 1 EOF @@ -364,7 +364,7 @@ test_expect_success 'fetch --atomic --prune executes a single reference transact $ZERO_OID $head_oid refs/remotes/origin/new-branch EOF - write_script atomic/.git/hooks/reference-transaction <<-\EOF && + test_hook -C atomic reference-transaction <<-\EOF && ( echo "$*" && cat ) >>actual EOF diff --git a/t/t5516-fetch-push.sh b/t/t5516-fetch-push.sh index 3137eb8d4d..4dfb080433 100755 --- a/t/t5516-fetch-push.sh +++ b/t/t5516-fetch-push.sh @@ -23,14 +23,10 @@ D=$(pwd) mk_empty () { repo_name="$1" - rm -fr "$repo_name" && - mkdir "$repo_name" && - ( - cd "$repo_name" && - git init && - git config receive.denyCurrentBranch warn && - mv .git/hooks .git/hooks-disabled - ) + test_when_finished "rm -rf \"$repo_name\"" && + test_path_is_missing "$repo_name" && + git init "$repo_name" && + git -C "$repo_name" config receive.denyCurrentBranch warn } mk_test () { @@ -59,40 +55,28 @@ mk_test () { mk_test_with_hooks() { repo_name=$1 mk_test "$@" && - ( - cd "$repo_name" && - mkdir .git/hooks && - cd .git/hooks && - - cat >pre-receive <<-'EOF' && - #!/bin/sh - cat - >>pre-receive.actual - EOF - - cat >update <<-'EOF' && - #!/bin/sh - printf "%s %s %s\n" "$@" >>update.actual - EOF - - cat >post-receive <<-'EOF' && - #!/bin/sh - cat - >>post-receive.actual - EOF - - cat >post-update <<-'EOF' && - #!/bin/sh - for ref in "$@" - do - printf "%s\n" "$ref" >>post-update.actual - done - EOF - - chmod +x pre-receive update post-receive post-update - ) + test_hook -C "$repo_name" pre-receive <<-'EOF' && + cat - >>pre-receive.actual + EOF + + test_hook -C "$repo_name" update <<-'EOF' && + printf "%s %s %s\n" "$@" >>update.actual + EOF + + test_hook -C "$repo_name" post-receive <<-'EOF' && + cat - >>post-receive.actual + EOF + + test_hook -C "$repo_name" post-update <<-'EOF' + for ref in "$@" + do + printf "%s\n" "$ref" >>post-update.actual + done + EOF } mk_child() { - rm -rf "$2" && + test_when_finished "rm -rf \"$2\"" && git clone "$1" "$2" } @@ -197,32 +181,32 @@ grep_wrote () { grep 'write_pack_file/wrote.*"value":"'$1'"' $2 } -test_expect_success 'push with negotiation' ' - # Without negotiation +test_expect_success 'push without negotiation' ' mk_empty testrepo && git push testrepo $the_first_commit:refs/remotes/origin/first_commit && test_commit -C testrepo unrelated_commit && git -C testrepo config receive.hideRefs refs/remotes/origin/first_commit && - echo now pushing without negotiation && + test_when_finished "rm event" && GIT_TRACE2_EVENT="$(pwd)/event" git -c protocol.version=2 push testrepo refs/heads/main:refs/remotes/origin/main && - grep_wrote 5 event && # 2 commits, 2 trees, 1 blob + grep_wrote 5 event # 2 commits, 2 trees, 1 blob +' - # Same commands, but with negotiation - rm event && +test_expect_success 'push with negotiation' ' mk_empty testrepo && git push testrepo $the_first_commit:refs/remotes/origin/first_commit && test_commit -C testrepo unrelated_commit && git -C testrepo config receive.hideRefs refs/remotes/origin/first_commit && + test_when_finished "rm event" && GIT_TRACE2_EVENT="$(pwd)/event" git -c protocol.version=2 -c push.negotiate=1 push testrepo refs/heads/main:refs/remotes/origin/main && grep_wrote 2 event # 1 commit, 1 tree ' test_expect_success 'push with negotiation proceeds anyway even if negotiation fails' ' - rm event && mk_empty testrepo && git push testrepo $the_first_commit:refs/remotes/origin/first_commit && test_commit -C testrepo unrelated_commit && git -C testrepo config receive.hideRefs refs/remotes/origin/first_commit && + test_when_finished "rm event" && GIT_TEST_PROTOCOL_VERSION=0 GIT_TRACE2_EVENT="$(pwd)/event" \ git -c push.negotiate=1 push testrepo refs/heads/main:refs/remotes/origin/main 2>err && grep_wrote 5 event && # 2 commits, 2 trees, 1 blob @@ -668,7 +652,6 @@ test_expect_success 'push does not update local refs on failure' ' mk_test testrepo heads/main && mk_child testrepo child && - mkdir testrepo/.git/hooks && echo "#!/no/frobnication/today" >testrepo/.git/hooks/pre-receive && chmod +x testrepo/.git/hooks/pre-receive && ( @@ -1330,7 +1313,7 @@ done test_expect_success 'fetch follows tags by default' ' mk_test testrepo heads/main && - rm -fr src dst && + test_when_finished "rm -rf src" && git init src && ( cd src && @@ -1340,6 +1323,7 @@ test_expect_success 'fetch follows tags by default' ' sed -n "p; s|refs/heads/main$|refs/remotes/origin/main|p" tmp1 | sort -k 3 >../expect ) && + test_when_finished "rm -rf dst" && git init dst && ( cd dst && @@ -1365,8 +1349,9 @@ test_expect_success 'peeled advertisements are not considered ref tips' ' test_expect_success 'pushing a specific ref applies remote.$name.push as refmap' ' mk_test testrepo heads/main && - rm -fr src dst && + test_when_finished "rm -rf src" && git init src && + test_when_finished "rm -rf dst" && git init --bare dst && ( cd src && @@ -1389,8 +1374,9 @@ test_expect_success 'pushing a specific ref applies remote.$name.push as refmap' test_expect_success 'with no remote.$name.push, it is not used as refmap' ' mk_test testrepo heads/main && - rm -fr src dst && + test_when_finished "rm -rf src" && git init src && + test_when_finished "rm -rf dst" && git init --bare dst && ( cd src && @@ -1411,8 +1397,9 @@ test_expect_success 'with no remote.$name.push, it is not used as refmap' ' test_expect_success 'with no remote.$name.push, upstream mapping is used' ' mk_test testrepo heads/main && - rm -fr src dst && + test_when_finished "rm -rf src" && git init src && + test_when_finished "rm -rf dst" && git init --bare dst && ( cd src && @@ -1440,8 +1427,9 @@ test_expect_success 'with no remote.$name.push, upstream mapping is used' ' test_expect_success 'push does not follow tags by default' ' mk_test testrepo heads/main && - rm -fr src dst && + test_when_finished "rm -rf src" && git init src && + test_when_finished "rm -rf dst" && git init --bare dst && ( cd src && @@ -1463,8 +1451,9 @@ test_expect_success 'push does not follow tags by default' ' test_expect_success 'push --follow-tags only pushes relevant tags' ' mk_test testrepo heads/main && - rm -fr src dst && + test_when_finished "rm -rf src" && git init src && + test_when_finished "rm -rf dst" && git init --bare dst && ( cd src && @@ -1502,9 +1491,9 @@ EOF ' test_expect_success 'pushing a tag pushes the tagged object' ' - rm -rf dst.git && blob=$(echo unreferenced | git hash-object -w --stdin) && git tag -m foo tag-of-blob $blob && + test_when_finished "rm -rf dst.git" && git init --bare dst.git && git push dst.git tag-of-blob && # the receiving index-pack should have noticed @@ -1515,7 +1504,7 @@ test_expect_success 'pushing a tag pushes the tagged object' ' ' test_expect_success 'push into bare respects core.logallrefupdates' ' - rm -rf dst.git && + test_when_finished "rm -rf dst.git" && git init --bare dst.git && git -C dst.git config core.logallrefupdates true && @@ -1533,7 +1522,7 @@ test_expect_success 'push into bare respects core.logallrefupdates' ' ' test_expect_success 'fetch into bare respects core.logallrefupdates' ' - rm -rf dst.git && + test_when_finished "rm -rf dst.git" && git init --bare dst.git && ( cd dst.git && @@ -1554,6 +1543,7 @@ test_expect_success 'fetch into bare respects core.logallrefupdates' ' ' test_expect_success 'receive.denyCurrentBranch = updateInstead' ' + mk_empty testrepo && git push testrepo main && ( cd testrepo && @@ -1656,7 +1646,7 @@ test_expect_success 'receive.denyCurrentBranch = updateInstead' ' ) && # (5) push into void - rm -fr void && + test_when_finished "rm -rf void" && git init void && ( cd void && @@ -1678,26 +1668,23 @@ test_expect_success 'receive.denyCurrentBranch = updateInstead' ' ' test_expect_success 'updateInstead with push-to-checkout hook' ' - rm -fr testrepo && + test_when_finished "rm -rf testrepo" && git init testrepo && - ( - cd testrepo && - git pull .. main && - git reset --hard HEAD^^ && - git tag initial && - git config receive.denyCurrentBranch updateInstead && - write_script .git/hooks/push-to-checkout <<-\EOF - echo >&2 updating from $(git rev-parse HEAD) - echo >&2 updating to "$1" - - git update-index -q --refresh && - git read-tree -u -m HEAD "$1" || { - status=$? - echo >&2 read-tree failed - exit $status - } - EOF - ) && + git -C testrepo pull .. main && + git -C testrepo reset --hard HEAD^^ && + git -C testrepo tag initial && + git -C testrepo config receive.denyCurrentBranch updateInstead && + test_hook -C testrepo push-to-checkout <<-\EOF && + echo >&2 updating from $(git rev-parse HEAD) + echo >&2 updating to "$1" + + git update-index -q --refresh && + git read-tree -u -m HEAD "$1" || { + status=$? + echo >&2 read-tree failed + exit $status + } + EOF # Try pushing into a pristine git push testrepo main && @@ -1740,35 +1727,32 @@ test_expect_success 'updateInstead with push-to-checkout hook' ' ) && # push into void - rm -fr void && + test_when_finished "rm -rf void" && git init void && - ( - cd void && - git config receive.denyCurrentBranch updateInstead && - write_script .git/hooks/push-to-checkout <<-\EOF - if git rev-parse --quiet --verify HEAD - then - has_head=yes - echo >&2 updating from $(git rev-parse HEAD) - else - has_head=no - echo >&2 pushing into void - fi - echo >&2 updating to "$1" - - git update-index -q --refresh && - case "$has_head" in - yes) - git read-tree -u -m HEAD "$1" ;; - no) - git read-tree -u -m "$1" ;; - esac || { - status=$? - echo >&2 read-tree failed - exit $status - } - EOF - ) && + git -C void config receive.denyCurrentBranch updateInstead && + test_hook -C void push-to-checkout <<-\EOF && + if git rev-parse --quiet --verify HEAD + then + has_head=yes + echo >&2 updating from $(git rev-parse HEAD) + else + has_head=no + echo >&2 pushing into void + fi + echo >&2 updating to "$1" + + git update-index -q --refresh && + case "$has_head" in + yes) + git read-tree -u -m HEAD "$1" ;; + no) + git read-tree -u -m "$1" ;; + esac || { + status=$? + echo >&2 read-tree failed + exit $status + } + EOF git push void main && ( diff --git a/t/t5521-pull-options.sh b/t/t5521-pull-options.sh index 66cfcb09c5..264de29c35 100755 --- a/t/t5521-pull-options.sh +++ b/t/t5521-pull-options.sh @@ -233,7 +233,7 @@ test_expect_success 'git pull --no-verify flag passed to merge' ' git init src && test_commit -C src one && git clone src dst && - write_script dst/.git/hooks/commit-msg <<-\EOF && + test_hook -C dst commit-msg <<-\EOF && false EOF test_commit -C src two && @@ -245,7 +245,7 @@ test_expect_success 'git pull --no-verify --verify passed to merge' ' git init src && test_commit -C src one && git clone src dst && - write_script dst/.git/hooks/commit-msg <<-\EOF && + test_hook -C dst commit-msg <<-\EOF && false EOF test_commit -C src two && diff --git a/t/t5526-fetch-submodules.sh b/t/t5526-fetch-submodules.sh index 840c89cc8b..43dada8544 100755 --- a/t/t5526-fetch-submodules.sh +++ b/t/t5526-fetch-submodules.sh @@ -10,33 +10,122 @@ export GIT_TEST_FATAL_REGISTER_SUBMODULE_ODB pwd=$(pwd) -add_upstream_commit() { +write_expected_sub () { + NEW_HEAD=$1 && + SUPER_HEAD=$2 && + cat >"$pwd/expect.err.sub" <<-EOF + Fetching submodule submodule${SUPER_HEAD:+ at commit $SUPER_HEAD} + From $pwd/submodule + OLD_HEAD..$NEW_HEAD sub -> origin/sub + EOF +} + +write_expected_sub2 () { + NEW_HEAD=$1 && + SUPER_HEAD=$2 && + cat >"$pwd/expect.err.sub2" <<-EOF + Fetching submodule submodule2${SUPER_HEAD:+ at commit $SUPER_HEAD} + From $pwd/submodule2 + OLD_HEAD..$NEW_HEAD sub2 -> origin/sub2 + EOF +} + +write_expected_deep () { + NEW_HEAD=$1 && + SUB_HEAD=$2 && + cat >"$pwd/expect.err.deep" <<-EOF + Fetching submodule submodule/subdir/deepsubmodule${SUB_HEAD:+ at commit $SUB_HEAD} + From $pwd/deepsubmodule + OLD_HEAD..$NEW_HEAD deep -> origin/deep + EOF +} + +write_expected_super () { + NEW_HEAD=$1 && + cat >"$pwd/expect.err.super" <<-EOF + From $pwd/. + OLD_HEAD..$NEW_HEAD super -> origin/super + EOF +} + +# For each submodule in the test setup, this creates a commit and writes +# a file that contains the expected err if that new commit were fetched. +# These output files get concatenated in the right order by +# verify_fetch_result(). +add_submodule_commits () { ( cd submodule && - head1=$(git rev-parse --short HEAD) && echo new >> subfile && test_tick && git add subfile && git commit -m new subfile && - head2=$(git rev-parse --short HEAD) && - echo "Fetching submodule submodule" > ../expect.err && - echo "From $pwd/submodule" >> ../expect.err && - echo " $head1..$head2 sub -> origin/sub" >> ../expect.err + new_head=$(git rev-parse --short HEAD) && + write_expected_sub $new_head ) && ( cd deepsubmodule && - head1=$(git rev-parse --short HEAD) && echo new >> deepsubfile && test_tick && git add deepsubfile && git commit -m new deepsubfile && - head2=$(git rev-parse --short HEAD) && - echo "Fetching submodule submodule/subdir/deepsubmodule" >> ../expect.err - echo "From $pwd/deepsubmodule" >> ../expect.err && - echo " $head1..$head2 deep -> origin/deep" >> ../expect.err + new_head=$(git rev-parse --short HEAD) && + write_expected_deep $new_head ) } +# For each superproject in the test setup, update its submodule, add the +# submodule and create a new commit with the submodule change. +# +# This requires add_submodule_commits() to be called first, otherwise +# the submodules will not have changed and cannot be "git add"-ed. +add_superproject_commits () { + ( + cd submodule && + ( + cd subdir/deepsubmodule && + git fetch && + git checkout -q FETCH_HEAD + ) && + git add subdir/deepsubmodule && + git commit -m "new deep submodule" + ) && + git add submodule && + git commit -m "new submodule" && + super_head=$(git rev-parse --short HEAD) && + sub_head=$(git -C submodule rev-parse --short HEAD) && + write_expected_super $super_head && + write_expected_sub $sub_head +} + +# Verifies that the expected repositories were fetched. This is done by +# concatenating the files expect.err.[super|sub|deep] in the correct +# order and comparing it to the actual stderr. +# +# If a repo should not be fetched in the test, its corresponding +# expect.err file should be rm-ed. +verify_fetch_result () { + ACTUAL_ERR=$1 && + rm -f expect.err.combined && + if test -f expect.err.super + then + cat expect.err.super >>expect.err.combined + fi && + if test -f expect.err.sub + then + cat expect.err.sub >>expect.err.combined + fi && + if test -f expect.err.deep + then + cat expect.err.deep >>expect.err.combined + fi && + if test -f expect.err.sub2 + then + cat expect.err.sub2 >>expect.err.combined + fi && + sed -e 's/[0-9a-f][0-9a-f]*\.\./OLD_HEAD\.\./' "$ACTUAL_ERR" >actual.err.cmp && + test_cmp expect.err.combined actual.err.cmp +} + test_expect_success setup ' mkdir deepsubmodule && ( @@ -68,38 +157,38 @@ test_expect_success setup ' ' test_expect_success "fetch --recurse-submodules recurses into submodules" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git fetch --recurse-submodules >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "submodule.recurse option triggers recursive fetch" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git -c submodule.recurse fetch >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "fetch --recurse-submodules -j2 has the same output behaviour" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && GIT_TRACE="$TRASH_DIRECTORY/trace.out" git fetch --recurse-submodules -j2 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err && + verify_fetch_result actual.err && grep "2 tasks" trace.out ' test_expect_success "fetch alone only fetches superproject" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git fetch >../actual.out 2>../actual.err @@ -124,11 +213,11 @@ test_expect_success "using fetchRecurseSubmodules=true in .gitmodules recurses i git fetch >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "--no-recurse-submodules overrides .gitmodules config" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git fetch --no-recurse-submodules >../actual.out 2>../actual.err @@ -155,7 +244,7 @@ test_expect_success "--recurse-submodules overrides fetchRecurseSubmodules setti git config --unset submodule.submodule.fetchRecurseSubmodules ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "--quiet propagates to submodules" ' @@ -177,13 +266,13 @@ test_expect_success "--quiet propagates to parallel submodules" ' ' test_expect_success "--dry-run propagates to submodules" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git fetch --recurse-submodules --dry-run >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "Without --dry-run propagates to submodules" ' @@ -192,22 +281,22 @@ test_expect_success "Without --dry-run propagates to submodules" ' git fetch --recurse-submodules >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "recurseSubmodules=true propagates into submodules" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git config fetch.recurseSubmodules true && git fetch >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "--recurse-submodules overrides config in submodule" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && ( @@ -217,11 +306,11 @@ test_expect_success "--recurse-submodules overrides config in submodule" ' git fetch --recurse-submodules >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err ' test_expect_success "--no-recurse-submodules overrides config setting" ' - add_upstream_commit && + add_submodule_commits && ( cd downstream && git config fetch.recurseSubmodules true && @@ -246,36 +335,34 @@ test_expect_success "Recursion doesn't happen when no new commits are fetched in ' test_expect_success "Recursion stops when no new submodule commits are fetched" ' - head1=$(git rev-parse --short HEAD) && git add submodule && git commit -m "new submodule" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.sub && - echo " $head1..$head2 super -> origin/super" >>expect.err.sub && - head -3 expect.err >> expect.err.sub && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.deep && ( cd downstream && git fetch >../actual.out 2>../actual.err ) && - test_cmp expect.err.sub actual.err && + verify_fetch_result actual.err && test_must_be_empty actual.out ' test_expect_success "Recursion doesn't happen when new superproject commits don't change any submodules" ' - add_upstream_commit && - head1=$(git rev-parse --short HEAD) && + add_submodule_commits && echo a > file && git add file && git commit -m "new file" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.file && - echo " $head1..$head2 super -> origin/super" >> expect.err.file && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.sub && + rm expect.err.deep && ( cd downstream && git fetch >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err.file actual.err + verify_fetch_result actual.err ' test_expect_success "Recursion picks up config in submodule" ' @@ -287,14 +374,11 @@ test_expect_success "Recursion picks up config in submodule" ' git config fetch.recurseSubmodules true ) ) && - add_upstream_commit && - head1=$(git rev-parse --short HEAD) && + add_submodule_commits && git add submodule && git commit -m "new submodule" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.sub && - echo " $head1..$head2 super -> origin/super" >> expect.err.sub && - cat expect.err >> expect.err.sub && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && ( cd downstream && git fetch >../actual.out 2>../actual.err && @@ -303,60 +387,23 @@ test_expect_success "Recursion picks up config in submodule" ' git config --unset fetch.recurseSubmodules ) ) && - test_cmp expect.err.sub actual.err && + verify_fetch_result actual.err && test_must_be_empty actual.out ' test_expect_success "Recursion picks up all submodules when necessary" ' - add_upstream_commit && - ( - cd submodule && - ( - cd subdir/deepsubmodule && - git fetch && - git checkout -q FETCH_HEAD - ) && - head1=$(git rev-parse --short HEAD^) && - git add subdir/deepsubmodule && - git commit -m "new deepsubmodule" && - head2=$(git rev-parse --short HEAD) && - echo "Fetching submodule submodule" > ../expect.err.sub && - echo "From $pwd/submodule" >> ../expect.err.sub && - echo " $head1..$head2 sub -> origin/sub" >> ../expect.err.sub - ) && - head1=$(git rev-parse --short HEAD) && - git add submodule && - git commit -m "new submodule" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.2 && - echo " $head1..$head2 super -> origin/super" >> expect.err.2 && - cat expect.err.sub >> expect.err.2 && - tail -3 expect.err >> expect.err.2 && + add_submodule_commits && + add_superproject_commits && ( cd downstream && git fetch >../actual.out 2>../actual.err ) && - test_cmp expect.err.2 actual.err && + verify_fetch_result actual.err && test_must_be_empty actual.out ' test_expect_success "'--recurse-submodules=on-demand' doesn't recurse when no new commits are fetched in the superproject (and ignores config)" ' - add_upstream_commit && - ( - cd submodule && - ( - cd subdir/deepsubmodule && - git fetch && - git checkout -q FETCH_HEAD - ) && - head1=$(git rev-parse --short HEAD^) && - git add subdir/deepsubmodule && - git commit -m "new deepsubmodule" && - head2=$(git rev-parse --short HEAD) && - echo Fetching submodule submodule > ../expect.err.sub && - echo "From $pwd/submodule" >> ../expect.err.sub && - echo " $head1..$head2 sub -> origin/sub" >> ../expect.err.sub - ) && + add_submodule_commits && ( cd downstream && git config fetch.recurseSubmodules true && @@ -368,15 +415,8 @@ test_expect_success "'--recurse-submodules=on-demand' doesn't recurse when no ne ' test_expect_success "'--recurse-submodules=on-demand' recurses as deep as necessary (and ignores config)" ' - head1=$(git rev-parse --short HEAD) && - git add submodule && - git commit -m "new submodule" && - head2=$(git rev-parse --short HEAD) && - tail -3 expect.err > expect.err.deepsub && - echo "From $pwd/." > expect.err && - echo " $head1..$head2 super -> origin/super" >>expect.err && - cat expect.err.sub >> expect.err && - cat expect.err.deepsub >> expect.err && + add_submodule_commits && + add_superproject_commits && ( cd downstream && git config fetch.recurseSubmodules false && @@ -392,24 +432,165 @@ test_expect_success "'--recurse-submodules=on-demand' recurses as deep as necess ) ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err + verify_fetch_result actual.err +' + +# These tests verify that we can fetch submodules that aren't in the +# index. +# +# First, test the simple case where the index is empty and we only fetch +# submodules that are not in the index. +test_expect_success 'setup downstream branch without submodules' ' + ( + cd downstream && + git checkout --recurse-submodules -b no-submodules && + git rm .gitmodules && + git rm submodule && + git commit -m "no submodules" && + git checkout --recurse-submodules super + ) +' + +test_expect_success "'--recurse-submodules=on-demand' should fetch submodule commits if the submodule is changed but the index has no submodules" ' + add_submodule_commits && + add_superproject_commits && + # Fetch the new superproject commit + ( + cd downstream && + git switch --recurse-submodules no-submodules && + git fetch --recurse-submodules=on-demand >../actual.out 2>../actual.err + ) && + super_head=$(git rev-parse --short HEAD) && + sub_head=$(git -C submodule rev-parse --short HEAD) && + deep_head=$(git -C submodule/subdir/deepsubmodule rev-parse --short HEAD) && + + # assert that these are fetched from commits, not the index + write_expected_sub $sub_head $super_head && + write_expected_deep $deep_head $sub_head && + + test_must_be_empty actual.out && + verify_fetch_result actual.err +' + +test_expect_success "'--recurse-submodules' should fetch submodule commits if the submodule is changed but the index has no submodules" ' + add_submodule_commits && + add_superproject_commits && + # Fetch the new superproject commit + ( + cd downstream && + git switch --recurse-submodules no-submodules && + git fetch --recurse-submodules >../actual.out 2>../actual.err + ) && + super_head=$(git rev-parse --short HEAD) && + sub_head=$(git -C submodule rev-parse --short HEAD) && + deep_head=$(git -C submodule/subdir/deepsubmodule rev-parse --short HEAD) && + + # assert that these are fetched from commits, not the index + write_expected_sub $sub_head $super_head && + write_expected_deep $deep_head $sub_head && + + test_must_be_empty actual.out && + verify_fetch_result actual.err +' + +test_expect_success "'--recurse-submodules' should ignore changed, inactive submodules" ' + add_submodule_commits && + add_superproject_commits && + + # Fetch the new superproject commit + ( + cd downstream && + git switch --recurse-submodules no-submodules && + git -c submodule.submodule.active=false fetch --recurse-submodules >../actual.out 2>../actual.err + ) && + test_must_be_empty actual.out && + super_head=$(git rev-parse --short HEAD) && + write_expected_super $super_head && + # Neither should be fetched because the submodule is inactive + rm expect.err.sub && + rm expect.err.deep && + verify_fetch_result actual.err +' + +# Now that we know we can fetch submodules that are not in the index, +# test that we can fetch index and non-index submodules in the same +# operation. +test_expect_success 'setup downstream branch with other submodule' ' + mkdir submodule2 && + ( + cd submodule2 && + git init && + echo sub2content >sub2file && + git add sub2file && + git commit -a -m new && + git branch -M sub2 + ) && + git checkout -b super-sub2-only && + git submodule add "$pwd/submodule2" submodule2 && + git commit -m "add sub2" && + git checkout super && + ( + cd downstream && + git fetch --recurse-submodules origin && + git checkout super-sub2-only && + # Explicitly run "git submodule update" because sub2 is new + # and has not been cloned. + git submodule update --init && + git checkout --recurse-submodules super + ) +' + +test_expect_success "'--recurse-submodules' should fetch submodule commits in changed submodules and the index" ' + test_when_finished "rm expect.err.sub2" && + # Create new commit in origin/super + add_submodule_commits && + add_superproject_commits && + + # Create new commit in origin/super-sub2-only + git checkout super-sub2-only && + ( + cd submodule2 && + test_commit --no-tag foo + ) && + git add submodule2 && + git commit -m "new submodule2" && + + git checkout super && + ( + cd downstream && + git fetch --recurse-submodules >../actual.out 2>../actual.err + ) && + test_must_be_empty actual.out && + sub2_head=$(git -C submodule2 rev-parse --short HEAD) && + super_head=$(git rev-parse --short super) && + super_sub2_only_head=$(git rev-parse --short super-sub2-only) && + write_expected_sub2 $sub2_head $super_sub2_only_head && + + # write_expected_super cannot handle >1 branch. Since this is a + # one-off, construct expect.err.super manually. + cat >"$pwd/expect.err.super" <<-EOF && + From $pwd/. + OLD_HEAD..$super_head super -> origin/super + OLD_HEAD..$super_sub2_only_head super-sub2-only -> origin/super-sub2-only + EOF + verify_fetch_result actual.err ' test_expect_success "'--recurse-submodules=on-demand' stops when no new submodule commits are found in the superproject (and ignores config)" ' - add_upstream_commit && - head1=$(git rev-parse --short HEAD) && + add_submodule_commits && echo a >> file && git add file && git commit -m "new file" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.file && - echo " $head1..$head2 super -> origin/super" >> expect.err.file && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.sub && + rm expect.err.deep && ( cd downstream && git fetch --recurse-submodules=on-demand >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err.file actual.err + verify_fetch_result actual.err ' test_expect_success "'fetch.recurseSubmodules=on-demand' overrides global config" ' @@ -417,15 +598,13 @@ test_expect_success "'fetch.recurseSubmodules=on-demand' overrides global config cd downstream && git fetch --recurse-submodules ) && - add_upstream_commit && + add_submodule_commits && git config --global fetch.recurseSubmodules false && - head1=$(git rev-parse --short HEAD) && git add submodule && git commit -m "new submodule" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.2 && - echo " $head1..$head2 super -> origin/super" >>expect.err.2 && - head -3 expect.err >> expect.err.2 && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.deep && ( cd downstream && git config fetch.recurseSubmodules on-demand && @@ -437,7 +616,7 @@ test_expect_success "'fetch.recurseSubmodules=on-demand' overrides global config git config --unset fetch.recurseSubmodules ) && test_must_be_empty actual.out && - test_cmp expect.err.2 actual.err + verify_fetch_result actual.err ' test_expect_success "'submodule.<sub>.fetchRecurseSubmodules=on-demand' overrides fetch.recurseSubmodules" ' @@ -445,15 +624,13 @@ test_expect_success "'submodule.<sub>.fetchRecurseSubmodules=on-demand' override cd downstream && git fetch --recurse-submodules ) && - add_upstream_commit && + add_submodule_commits && git config fetch.recurseSubmodules false && - head1=$(git rev-parse --short HEAD) && git add submodule && git commit -m "new submodule" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err.2 && - echo " $head1..$head2 super -> origin/super" >>expect.err.2 && - head -3 expect.err >> expect.err.2 && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.deep && ( cd downstream && git config submodule.submodule.fetchRecurseSubmodules on-demand && @@ -465,7 +642,7 @@ test_expect_success "'submodule.<sub>.fetchRecurseSubmodules=on-demand' override git config --unset submodule.submodule.fetchRecurseSubmodules ) && test_must_be_empty actual.out && - test_cmp expect.err.2 actual.err + verify_fetch_result actual.err ' test_expect_success "don't fetch submodule when newly recorded commits are already present" ' @@ -473,18 +650,19 @@ test_expect_success "don't fetch submodule when newly recorded commits are alrea cd submodule && git checkout -q HEAD^^ ) && - head1=$(git rev-parse --short HEAD) && git add submodule && git commit -m "submodule rewound" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." > expect.err && - echo " $head1..$head2 super -> origin/super" >> expect.err && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.sub && + # This file does not exist, but rm -f for readability + rm -f expect.err.deep && ( cd downstream && git fetch >../actual.out 2>../actual.err ) && test_must_be_empty actual.out && - test_cmp expect.err actual.err && + verify_fetch_result actual.err && ( cd submodule && git checkout -q sub @@ -496,15 +674,13 @@ test_expect_success "'fetch.recurseSubmodules=on-demand' works also without .git cd downstream && git fetch --recurse-submodules ) && - add_upstream_commit && - head1=$(git rev-parse --short HEAD) && + add_submodule_commits && git add submodule && git rm .gitmodules && git commit -m "new submodule without .gitmodules" && - head2=$(git rev-parse --short HEAD) && - echo "From $pwd/." >expect.err.2 && - echo " $head1..$head2 super -> origin/super" >>expect.err.2 && - head -3 expect.err >>expect.err.2 && + new_head=$(git rev-parse --short HEAD) && + write_expected_super $new_head && + rm expect.err.deep && ( cd downstream && rm .gitmodules && @@ -520,7 +696,7 @@ test_expect_success "'fetch.recurseSubmodules=on-demand' works also without .git git reset --hard ) && test_must_be_empty actual.out && - test_cmp expect.err.2 actual.err && + verify_fetch_result actual.err && git checkout HEAD^ -- .gitmodules && git add .gitmodules && git commit -m "new submodule restored .gitmodules" @@ -842,4 +1018,111 @@ test_expect_success 'recursive fetch after deinit a submodule' ' test_cmp expect actual ' +test_expect_success 'setup repo with upstreams that share a submodule name' ' + mkdir same-name-1 && + ( + cd same-name-1 && + git init -b main && + test_commit --no-tag a + ) && + git clone same-name-1 same-name-2 && + # same-name-1 and same-name-2 both add a submodule with the + # name "submodule" + ( + cd same-name-1 && + mkdir submodule && + git -C submodule init -b main && + test_commit -C submodule --no-tag a1 && + git submodule add "$pwd/same-name-1/submodule" && + git add submodule && + git commit -m "super-a1" + ) && + ( + cd same-name-2 && + mkdir submodule && + git -C submodule init -b main && + test_commit -C submodule --no-tag a2 && + git submodule add "$pwd/same-name-2/submodule" && + git add submodule && + git commit -m "super-a2" + ) && + git clone same-name-1 -o same-name-1 same-name-downstream && + ( + cd same-name-downstream && + git remote add same-name-2 ../same-name-2 && + git fetch --all && + # init downstream with same-name-1 + git submodule update --init + ) +' + +test_expect_success 'fetch --recurse-submodules updates name-conflicted, populated submodule' ' + test_when_finished "git -C same-name-downstream checkout main" && + ( + cd same-name-1 && + test_commit -C submodule --no-tag b1 && + git add submodule && + git commit -m "super-b1" + ) && + ( + cd same-name-2 && + test_commit -C submodule --no-tag b2 && + git add submodule && + git commit -m "super-b2" + ) && + ( + cd same-name-downstream && + # even though the .gitmodules is correct, we cannot + # fetch from same-name-2 + git checkout same-name-2/main && + git fetch --recurse-submodules same-name-1 && + test_must_fail git fetch --recurse-submodules same-name-2 + ) && + super_head1=$(git -C same-name-1 rev-parse HEAD) && + git -C same-name-downstream cat-file -e $super_head1 && + + super_head2=$(git -C same-name-2 rev-parse HEAD) && + git -C same-name-downstream cat-file -e $super_head2 && + + sub_head1=$(git -C same-name-1/submodule rev-parse HEAD) && + git -C same-name-downstream/submodule cat-file -e $sub_head1 && + + sub_head2=$(git -C same-name-2/submodule rev-parse HEAD) && + test_must_fail git -C same-name-downstream/submodule cat-file -e $sub_head2 +' + +test_expect_success 'fetch --recurse-submodules updates name-conflicted, unpopulated submodule' ' + ( + cd same-name-1 && + test_commit -C submodule --no-tag c1 && + git add submodule && + git commit -m "super-c1" + ) && + ( + cd same-name-2 && + test_commit -C submodule --no-tag c2 && + git add submodule && + git commit -m "super-c2" + ) && + ( + cd same-name-downstream && + git checkout main && + git rm .gitmodules && + git rm submodule && + git commit -m "no submodules" && + git fetch --recurse-submodules same-name-1 + ) && + head1=$(git -C same-name-1/submodule rev-parse HEAD) && + head2=$(git -C same-name-2/submodule rev-parse HEAD) && + ( + cd same-name-downstream/.git/modules/submodule && + # The submodule has core.worktree pointing to the "git + # rm"-ed directory, overwrite the invalid value. See + # comment in get_fetch_task_from_changed() for more + # information. + git --work-tree=. cat-file -e $head1 && + test_must_fail git --work-tree=. cat-file -e $head2 + ) +' + test_done diff --git a/t/t5534-push-signed.sh b/t/t5534-push-signed.sh index 24d374adba..7c0a148e73 100755 --- a/t/t5534-push-signed.sh +++ b/t/t5534-push-signed.sh @@ -35,8 +35,7 @@ test_expect_success setup ' test_expect_success 'unsigned push does not send push certificate' ' prepare_dst && - mkdir -p dst/.git/hooks && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -52,8 +51,7 @@ test_expect_success 'unsigned push does not send push certificate' ' test_expect_success 'talking with a receiver without push certificate support' ' prepare_dst && - mkdir -p dst/.git/hooks && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -69,22 +67,19 @@ test_expect_success 'talking with a receiver without push certificate support' ' test_expect_success 'push --signed fails with a receiver without push certificate support' ' prepare_dst && - mkdir -p dst/.git/hooks && test_must_fail git push --signed dst noop ff +noff 2>err && test_i18ngrep "the receiving end does not support" err ' test_expect_success 'push --signed=1 is accepted' ' prepare_dst && - mkdir -p dst/.git/hooks && test_must_fail git push --signed=1 dst noop ff +noff 2>err && test_i18ngrep "the receiving end does not support" err ' test_expect_success GPG 'no certificate for a signed push with no update' ' prepare_dst && - mkdir -p dst/.git/hooks && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && if test -n "${GIT_PUSH_CERT-}" then git cat-file blob $GIT_PUSH_CERT >../push-cert @@ -96,9 +91,8 @@ test_expect_success GPG 'no certificate for a signed push with no update' ' test_expect_success GPG 'signed push sends push certificate' ' prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -139,10 +133,9 @@ test_expect_success GPG 'signed push sends push certificate' ' test_expect_success GPGSSH 'ssh signed push sends push certificate' ' prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config gpg.ssh.allowedSignersFile "${GPGSSH_ALLOWED_SIGNERS}" && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -223,9 +216,8 @@ test_expect_success GPG 'inconsistent push options in signed push not allowed' ' test_expect_success GPG 'fail without key and heed user.signingkey' ' prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -273,9 +265,8 @@ test_expect_success GPG 'fail without key and heed user.signingkey' ' test_expect_success GPGSM 'fail without key and heed user.signingkey x509' ' test_config gpg.format x509 && prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -326,10 +317,9 @@ test_expect_success GPGSM 'fail without key and heed user.signingkey x509' ' test_expect_success GPGSSH 'fail without key and heed user.signingkey ssh' ' test_config gpg.format ssh && prepare_dst && - mkdir -p dst/.git/hooks && git -C dst config gpg.ssh.allowedSignersFile "${GPGSSH_ALLOWED_SIGNERS}" && git -C dst config receive.certnonceseed sekrit && - write_script dst/.git/hooks/post-receive <<-\EOF && + test_hook -C dst post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate diff --git a/t/t5537-fetch-shallow.sh b/t/t5537-fetch-shallow.sh index 11d5ea54a9..92948de7a0 100755 --- a/t/t5537-fetch-shallow.sh +++ b/t/t5537-fetch-shallow.sh @@ -161,6 +161,15 @@ test_expect_success 'fetch --update-shallow' ' ) ' +test_expect_success 'fetch --update-shallow into a repo with submodules' ' + git init a-submodule && + test_commit -C a-submodule foo && + git init repo-with-sub && + git -C repo-with-sub submodule add ../a-submodule a-submodule && + git -C repo-with-sub commit -m "added submodule" && + git -C repo-with-sub fetch --update-shallow ../shallow/.git refs/heads/*:refs/remotes/shallow/* +' + test_expect_success 'fetch --update-shallow (with fetch.writeCommitGraph)' ' ( cd shallow && diff --git a/t/t5540-http-push-webdav.sh b/t/t5540-http-push-webdav.sh index b0dbacf0b9..37db3dec0c 100755 --- a/t/t5540-http-push-webdav.sh +++ b/t/t5540-http-push-webdav.sh @@ -42,7 +42,9 @@ test_expect_success 'setup remote repository' ' git clone --bare test_repo test_repo.git && cd test_repo.git && git --bare update-server-info && - mv hooks/post-update.sample hooks/post-update && + test_hook --setup post-update <<-\EOF && + exec git update-server-info + EOF ORIG_HEAD=$(git rev-parse --verify HEAD) && cd - && mv test_repo.git "$HTTPD_DOCUMENT_ROOT_PATH" diff --git a/t/t5541-http-push-smart.sh b/t/t5541-http-push-smart.sh index 8ca50f8b18..2f09ff4fac 100755 --- a/t/t5541-http-push-smart.sh +++ b/t/t5541-http-push-smart.sh @@ -96,18 +96,18 @@ test_expect_success 'create and delete remote branch' ' test_must_fail git show-ref --verify refs/remotes/origin/dev ' -cat >"$HTTPD_DOCUMENT_ROOT_PATH/test_repo.git/hooks/update" <<EOF -#!/bin/sh -exit 1 -EOF -chmod a+x "$HTTPD_DOCUMENT_ROOT_PATH/test_repo.git/hooks/update" +test_expect_success 'setup rejected update hook' ' + test_hook --setup -C "$HTTPD_DOCUMENT_ROOT_PATH/test_repo.git" update <<-\EOF && + exit 1 + EOF -cat >exp <<EOF -remote: error: hook declined to update refs/heads/dev2 -To http://127.0.0.1:$LIB_HTTPD_PORT/smart/test_repo.git - ! [remote rejected] dev2 -> dev2 (hook declined) -error: failed to push some refs to 'http://127.0.0.1:$LIB_HTTPD_PORT/smart/test_repo.git' -EOF + cat >exp <<-EOF + remote: error: hook declined to update refs/heads/dev2 + To http://127.0.0.1:$LIB_HTTPD_PORT/smart/test_repo.git + ! [remote rejected] dev2 -> dev2 (hook declined) + error: failed to push some refs to '\''http://127.0.0.1:$LIB_HTTPD_PORT/smart/test_repo.git'\'' + EOF +' test_expect_success 'rejected update prints status' ' cd "$ROOT_PATH"/test_repo_clone && @@ -419,10 +419,7 @@ test_expect_success CMDLINE_LIMIT 'push 2000 tags over http' ' ' test_expect_success GPG 'push with post-receive to inspect certificate' ' - ( - cd "$HTTPD_DOCUMENT_ROOT_PATH"/test_repo.git && - mkdir -p hooks && - write_script hooks/post-receive <<-\EOF && + test_hook -C "$HTTPD_DOCUMENT_ROOT_PATH"/test_repo.git post-receive <<-\EOF && # discard the update list cat >/dev/null # record the push certificate @@ -437,8 +434,9 @@ test_expect_success GPG 'push with post-receive to inspect certificate' ' NONCE_STATUS=${GIT_PUSH_CERT_NONCE_STATUS-nononcestatus} NONCE=${GIT_PUSH_CERT_NONCE-nononce} E_O_F - EOF - + EOF + ( + cd "$HTTPD_DOCUMENT_ROOT_PATH"/test_repo.git && git config receive.certnonceseed sekrit && git config receive.certnonceslop 30 ) && diff --git a/t/t5543-atomic-push.sh b/t/t5543-atomic-push.sh index bfee461861..70431122a4 100755 --- a/t/t5543-atomic-push.sh +++ b/t/t5543-atomic-push.sh @@ -162,16 +162,10 @@ test_expect_success 'atomic push obeys update hook preventing a branch to be pus test_commit two && git push --mirror up ) && - ( - cd upstream && - HOOKDIR="$(git rev-parse --git-dir)/hooks" && - HOOK="$HOOKDIR/update" && - mkdir -p "$HOOKDIR" && - write_script "$HOOK" <<-\EOF - # only allow update to main from now on - test "$1" = "refs/heads/main" - EOF - ) && + test_hook -C upstream update <<-\EOF && + # only allow update to main from now on + test "$1" = "refs/heads/main" + EOF ( cd workbench && git checkout main && diff --git a/t/t5547-push-quarantine.sh b/t/t5547-push-quarantine.sh index faaa51ccc5..1876fb34e5 100755 --- a/t/t5547-push-quarantine.sh +++ b/t/t5547-push-quarantine.sh @@ -5,7 +5,7 @@ test_description='check quarantine of objects during push' test_expect_success 'create picky dest repo' ' git init --bare dest.git && - write_script dest.git/hooks/pre-receive <<-\EOF + test_hook --setup -C dest.git pre-receive <<-\EOF while read old new ref; do test "$(git log -1 --format=%s $new)" = reject && exit 1 done @@ -60,7 +60,7 @@ test_expect_success 'push to repo path with path separator (colon)' ' test_expect_success 'updating a ref from quarantine is forbidden' ' git init --bare update.git && - write_script update.git/hooks/pre-receive <<-\EOF && + test_hook -C update.git pre-receive <<-\EOF && read old new refname git update-ref refs/heads/unrelated $new exit 1 diff --git a/t/t5548-push-porcelain.sh b/t/t5548-push-porcelain.sh index f11ff57e54..6282728eaf 100755 --- a/t/t5548-push-porcelain.sh +++ b/t/t5548-push-porcelain.sh @@ -168,7 +168,7 @@ run_git_push_porcelain_output_test() { ' test_expect_success "prepare pre-receive hook ($PROTOCOL)" ' - write_script "$upstream/hooks/pre-receive" <<-EOF + test_hook --setup -C "$upstream" pre-receive <<-EOF exit 1 EOF ' diff --git a/t/t5550-http-fetch-dumb.sh b/t/t5550-http-fetch-dumb.sh index 259203926a..f0d9cd584d 100755 --- a/t/t5550-http-fetch-dumb.sh +++ b/t/t5550-http-fetch-dumb.sh @@ -25,16 +25,17 @@ test_expect_success 'setup repository' ' git commit -m two ' +setup_post_update_server_info_hook () { + test_hook --setup -C "$1" post-update <<-\EOF && + exec git update-server-info + EOF + git -C "$1" update-server-info +} + test_expect_success 'create http-accessible bare repository with loose objects' ' cp -R .git "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" && - (cd "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" && - git config core.bare true && - mkdir -p hooks && - write_script "hooks/post-update" <<-\EOF && - exec git update-server-info - EOF - hooks/post-update - ) && + git -C "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" config core.bare true && + setup_post_update_server_info_hook "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" && git remote add public "$HTTPD_DOCUMENT_ROOT_PATH/repo.git" && git push public main:main ' @@ -62,13 +63,7 @@ test_expect_success 'create password-protected repository' ' test_expect_success 'create empty remote repository' ' git init --bare "$HTTPD_DOCUMENT_ROOT_PATH/empty.git" && - (cd "$HTTPD_DOCUMENT_ROOT_PATH/empty.git" && - mkdir -p hooks && - write_script "hooks/post-update" <<-\EOF && - exec git update-server-info - EOF - hooks/post-update - ) + setup_post_update_server_info_hook "$HTTPD_DOCUMENT_ROOT_PATH/empty.git" ' test_expect_success 'empty dumb HTTP repository has default hash algorithm' ' diff --git a/t/t5571-pre-push-hook.sh b/t/t5571-pre-push-hook.sh index 96d6ecc0af..a11b20e378 100755 --- a/t/t5571-pre-push-hook.sh +++ b/t/t5571-pre-push-hook.sh @@ -6,16 +6,11 @@ export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME . ./test-lib.sh -# Setup hook that always succeeds -HOOKDIR="$(git rev-parse --git-dir)/hooks" -HOOK="$HOOKDIR/pre-push" -mkdir -p "$HOOKDIR" -write_script "$HOOK" <<EOF -cat >actual -exit 0 -EOF - test_expect_success 'setup' ' + test_hook pre-push <<-\EOF && + cat >actual + EOF + git config push.default upstream && git init --bare repo1 && git remote add parent1 repo1 && @@ -28,15 +23,16 @@ test_expect_success 'setup' ' git push parent1 HEAD:foreign && test_cmp expect actual ' -write_script "$HOOK" <<EOF -cat >actual -exit 1 -EOF COMMIT1="$(git rev-parse HEAD)" export COMMIT1 test_expect_success 'push with failing hook' ' + test_hook pre-push <<-\EOF && + cat >actual && + exit 1 + EOF + test_commit two && cat >expect <<-EOF && HEAD $(git rev-parse HEAD) refs/heads/main $(test_oid zero) @@ -55,13 +51,13 @@ test_expect_success '--no-verify bypasses hook' ' COMMIT2="$(git rev-parse HEAD)" export COMMIT2 -write_script "$HOOK" <<'EOF' -echo "$1" >actual -echo "$2" >>actual -cat >>actual -EOF - test_expect_success 'push with hook' ' + test_hook --setup pre-push <<-\EOF && + echo "$1" >actual + echo "$2" >>actual + cat >>actual + EOF + cat >expect <<-EOF && parent1 repo1 @@ -136,7 +132,9 @@ test_expect_success 'set up many-ref tests' ' ' test_expect_success 'sigpipe does not cause pre-push hook failure' ' - echo "exit 0" | write_script "$HOOK" && + test_hook --clobber pre-push <<-\EOF && + exit 0 + EOF git push parent1 "refs/heads/b/*:refs/heads/b/*" ' diff --git a/t/t5601-clone.sh b/t/t5601-clone.sh index 83c24fc97a..4a61f2c901 100755 --- a/t/t5601-clone.sh +++ b/t/t5601-clone.sh @@ -79,12 +79,10 @@ test_expect_success 'clone from hooks' ' cd .. && git init r1 && cd r1 && - cat >.git/hooks/pre-commit <<-\EOF && - #!/bin/sh + test_hook pre-commit <<-\EOF && git clone ../r0 ../r2 exit 1 EOF - chmod u+x .git/hooks/pre-commit && : >file && git add file && test_must_fail git commit -m invoke-hook && diff --git a/t/t6120-describe.sh b/t/t6120-describe.sh index 9781b92aed..9a35e783a7 100755 --- a/t/t6120-describe.sh +++ b/t/t6120-describe.sh @@ -488,6 +488,124 @@ test_expect_success 'name-rev covers all conditions while looking at parents' ' ) ' +# A-B-C-D-E-main +# +# Where C has a non-monotonically increasing commit timestamp w.r.t. other +# commits +test_expect_success 'non-monotonic commit dates setup' ' + UNIX_EPOCH_ZERO="@0 +0000" && + git init non-monotonic && + test_commit -C non-monotonic A && + test_commit -C non-monotonic --no-tag B && + test_commit -C non-monotonic --no-tag --date "$UNIX_EPOCH_ZERO" C && + test_commit -C non-monotonic D && + test_commit -C non-monotonic E +' + +test_expect_success 'name-rev with commitGraph handles non-monotonic timestamps' ' + test_config -C non-monotonic core.commitGraph true && + ( + cd non-monotonic && + + git commit-graph write --reachable && + + echo "main~3 tags/D~2" >expect && + git name-rev --tags main~3 >actual && + + test_cmp expect actual + ) +' + +test_expect_success 'name-rev --all works with non-monotonic timestamps' ' + test_config -C non-monotonic core.commitGraph false && + ( + cd non-monotonic && + + rm -rf .git/info/commit-graph* && + + cat >tags <<-\EOF && + tags/E + tags/D + tags/D~1 + tags/D~2 + tags/A + EOF + + git log --pretty=%H >revs && + + paste -d" " revs tags | sort >expect && + + git name-rev --tags --all | sort >actual && + test_cmp expect actual + ) +' + +test_expect_success 'name-rev --annotate-stdin works with non-monotonic timestamps' ' + test_config -C non-monotonic core.commitGraph false && + ( + cd non-monotonic && + + rm -rf .git/info/commit-graph* && + + cat >expect <<-\EOF && + E + D + D~1 + D~2 + A + EOF + + git log --pretty=%H >revs && + git name-rev --tags --annotate-stdin --name-only <revs >actual && + test_cmp expect actual + ) +' + +test_expect_success 'name-rev --all works with commitGraph' ' + test_config -C non-monotonic core.commitGraph true && + ( + cd non-monotonic && + + git commit-graph write --reachable && + + cat >tags <<-\EOF && + tags/E + tags/D + tags/D~1 + tags/D~2 + tags/A + EOF + + git log --pretty=%H >revs && + + paste -d" " revs tags | sort >expect && + + git name-rev --tags --all | sort >actual && + test_cmp expect actual + ) +' + +test_expect_success 'name-rev --annotate-stdin works with commitGraph' ' + test_config -C non-monotonic core.commitGraph true && + ( + cd non-monotonic && + + git commit-graph write --reachable && + + cat >expect <<-\EOF && + E + D + D~1 + D~2 + A + EOF + + git log --pretty=%H >revs && + git name-rev --tags --annotate-stdin --name-only <revs >actual && + test_cmp expect actual + ) +' + # B # o # \ diff --git a/t/t6423-merge-rename-directories.sh b/t/t6423-merge-rename-directories.sh index 5b81a130e9..479db32cd6 100755 --- a/t/t6423-merge-rename-directories.sh +++ b/t/t6423-merge-rename-directories.sh @@ -4421,14 +4421,14 @@ test_setup_12c1 () { git checkout A && git mv node2/ node1/ && - for i in `git ls-files`; do echo side A >>$i; done && + for i in $(git ls-files); do echo side A >>$i; done && git add -u && test_tick && git commit -m "A" && git checkout B && git mv node1/ node2/ && - for i in `git ls-files`; do echo side B >>$i; done && + for i in $(git ls-files); do echo side B >>$i; done && git add -u && test_tick && git commit -m "B" @@ -4511,7 +4511,7 @@ test_setup_12c2 () { git checkout A && git mv node2/ node1/ && - for i in `git ls-files`; do echo side A >>$i; done && + for i in $(git ls-files); do echo side A >>$i; done && git add -u && echo leaf5 >node1/leaf5 && git add node1/leaf5 && @@ -4520,7 +4520,7 @@ test_setup_12c2 () { git checkout B && git mv node1/ node2/ && - for i in `git ls-files`; do echo side B >>$i; done && + for i in $(git ls-files); do echo side B >>$i; done && git add -u && echo leaf6 >node2/leaf6 && git add node2/leaf6 && @@ -4759,7 +4759,7 @@ test_setup_12f () { echo g >dir/subdir/tweaked/g && echo h >dir/subdir/tweaked/h && test_seq 20 30 >dir/subdir/tweaked/Makefile && - for i in `test_seq 1 88`; do + for i in $(test_seq 1 88); do echo content $i >dir/unchanged/file_$i done && git add . && diff --git a/t/t6500-gc.sh b/t/t6500-gc.sh index c2021267f2..cd6c53360d 100755 --- a/t/t6500-gc.sh +++ b/t/t6500-gc.sh @@ -101,12 +101,12 @@ test_expect_success 'pre-auto-gc hook can stop auto gc' ' EOF git init pre-auto-gc-hook && + test_hook -C pre-auto-gc-hook pre-auto-gc <<-\EOF && + echo >&2 no gc for you && + exit 1 + EOF ( cd pre-auto-gc-hook && - write_script ".git/hooks/pre-auto-gc" <<-\EOF && - echo >&2 no gc for you && - exit 1 - EOF git config gc.auto 3 && git config gc.autoDetach false && @@ -128,14 +128,12 @@ test_expect_success 'pre-auto-gc hook can stop auto gc' ' See "git help gc" for manual housekeeping. EOF - ( - cd pre-auto-gc-hook && - write_script ".git/hooks/pre-auto-gc" <<-\EOF && - echo >&2 will gc for you && - exit 0 - EOF - git gc --auto >../out.actual 2>../err.actual - ) && + test_hook -C pre-auto-gc-hook --clobber pre-auto-gc <<-\EOF && + echo >&2 will gc for you && + exit 0 + EOF + + git -C pre-auto-gc-hook gc --auto >out.actual 2>err.actual && test_must_be_empty out.actual && test_cmp err.expect err.actual diff --git a/t/t7102-reset.sh b/t/t7102-reset.sh index d05426062e..22477f3a31 100755 --- a/t/t7102-reset.sh +++ b/t/t7102-reset.sh @@ -462,14 +462,40 @@ test_expect_success 'resetting an unmodified path is a no-op' ' git diff-index --cached --exit-code HEAD ' +test_reset_refreshes_index () { + + # To test whether the index is refreshed in `git reset --mixed` with + # the given options, create a scenario where we clearly see different + # results depending on whether the refresh occurred or not. + + # Step 0: start with a clean index + git reset --hard HEAD && + + # Step 1: remove file2, but only in the index (no change to worktree) + git rm --cached file2 && + + # Step 2: reset index & leave worktree unchanged from HEAD + git $1 reset $2 --mixed HEAD && + + # Step 3: verify whether the index is refreshed by checking whether + # file2 still has staged changes in the index differing from HEAD (if + # the refresh occurred, there should be no such changes) + git diff-files >output.log && + test_must_be_empty output.log +} + test_expect_success '--mixed refreshes the index' ' - cat >expect <<-\EOF && - Unstaged changes after reset: - M file2 - EOF - echo 123 >>file2 && - git reset --mixed HEAD >output && - test_cmp expect output + # Verify default behavior (without --[no-]refresh or reset.refresh) + test_reset_refreshes_index && + + # With --quiet + test_reset_refreshes_index "" --quiet +' + +test_expect_success '--mixed --[no-]refresh sets refresh behavior' ' + # Verify that --[no-]refresh controls index refresh + test_reset_refreshes_index "" --refresh && + ! test_reset_refreshes_index "" --no-refresh ' test_expect_success '--mixed preserves skip-worktree' ' diff --git a/t/t7113-post-index-change-hook.sh b/t/t7113-post-index-change-hook.sh index a21781d68a..58e55a7c77 100755 --- a/t/t7113-post-index-change-hook.sh +++ b/t/t7113-post-index-change-hook.sh @@ -17,8 +17,7 @@ test_expect_success 'setup' ' ' test_expect_success 'test status, add, commit, others trigger hook without flags set' ' - mkdir -p .git/hooks && - write_script .git/hooks/post-index-change <<-\EOF && + test_hook post-index-change <<-\EOF && if test "$1" -eq 1; then echo "Invalid combination of flags passed to hook; updated_workdir is set." >testfailure exit 1 @@ -63,7 +62,7 @@ test_expect_success 'test status, add, commit, others trigger hook without flags ' test_expect_success 'test checkout and reset trigger the hook' ' - write_script .git/hooks/post-index-change <<-\EOF && + test_hook post-index-change <<-\EOF && if test "$1" -eq 1 && test "$2" -eq 1; then echo "Invalid combination of flags passed to hook; updated_workdir and updated_skipworktree are both set." >testfailure exit 1 @@ -106,7 +105,7 @@ test_expect_success 'test checkout and reset trigger the hook' ' ' test_expect_success 'test reset --mixed and update-index triggers the hook' ' - write_script .git/hooks/post-index-change <<-\EOF && + test_hook post-index-change <<-\EOF && if test "$1" -eq 1 && test "$2" -eq 1; then echo "Invalid combination of flags passed to hook; updated_workdir and updated_skipworktree are both set." >testfailure exit 1 diff --git a/t/t7406-submodule-update.sh b/t/t7406-submodule-update.sh index 11cccbb333..000e055811 100755 --- a/t/t7406-submodule-update.sh +++ b/t/t7406-submodule-update.sh @@ -205,8 +205,18 @@ test_expect_success 'submodule update should fail due to local changes' ' (cd submodule && compare_head ) && - test_must_fail git submodule update submodule - ) + test_must_fail git submodule update submodule 2>../actual.raw + ) && + sed "s/^> //" >expect <<-\EOF && + > error: Your local changes to the following files would be overwritten by checkout: + > file + > Please commit your changes or stash them before you switch branches. + > Aborting + > fatal: Unable to checkout OID in submodule path '\''submodule'\'' + EOF + sed -e "s/checkout $SQ[^$SQ]*$SQ/checkout OID/" <actual.raw >actual && + test_cmp expect actual + ' test_expect_success 'submodule update should throw away changes with --force ' ' (cd super && @@ -1061,4 +1071,16 @@ test_expect_success 'submodule update --quiet passes quietness to fetch with a s ) ' +test_expect_success 'submodule update --filter requires --init' ' + test_expect_code 129 git -C super submodule update --filter blob:none +' + +test_expect_success 'submodule update --filter sets partial clone settings' ' + test_when_finished "rm -rf super-filter" && + git clone cloned super-filter && + git -C super-filter submodule update --init --filter blob:none && + test_cmp_config -C super-filter/submodule true remote.origin.promisor && + test_cmp_config -C super-filter/submodule blob:none remote.origin.partialclonefilter +' + test_done diff --git a/t/t7408-submodule-reference.sh b/t/t7408-submodule-reference.sh index a3892f494b..c3a4545510 100755 --- a/t/t7408-submodule-reference.sh +++ b/t/t7408-submodule-reference.sh @@ -193,7 +193,19 @@ test_expect_success 'missing nested submodule alternate fails clone and submodul cd supersuper-clone && check_that_two_of_three_alternates_are_used && # update of the submodule fails - test_must_fail git submodule update --init --recursive + cat >expect <<-\EOF && + fatal: submodule '\''sub'\'' cannot add alternate: path ... does not exist + Failed to clone '\''sub'\''. Retry scheduled + fatal: submodule '\''sub-dissociate'\'' cannot add alternate: path ... does not exist + Failed to clone '\''sub-dissociate'\''. Retry scheduled + fatal: submodule '\''sub'\'' cannot add alternate: path ... does not exist + Failed to clone '\''sub'\'' a second time, aborting + fatal: Failed to recurse into submodule path ... + EOF + test_must_fail git submodule update --init --recursive 2>err && + grep -e fatal: -e ^Failed err >actual.raw && + sed -e "s/path $SQ[^$SQ]*$SQ/path .../" <actual.raw >actual && + test_cmp expect actual ) ' diff --git a/t/t7503-pre-commit-and-pre-merge-commit-hooks.sh b/t/t7503-pre-commit-and-pre-merge-commit-hooks.sh index 606d8d0f08..ad1eb64ba0 100755 --- a/t/t7503-pre-commit-and-pre-merge-commit-hooks.sh +++ b/t/t7503-pre-commit-and-pre-merge-commit-hooks.sh @@ -7,37 +7,6 @@ export GIT_TEST_DEFAULT_INITIAL_BRANCH_NAME . ./test-lib.sh -HOOKDIR="$(git rev-parse --git-dir)/hooks" -PRECOMMIT="$HOOKDIR/pre-commit" -PREMERGE="$HOOKDIR/pre-merge-commit" - -# Prepare sample scripts that write their $0 to actual_hooks -test_expect_success 'sample script setup' ' - mkdir -p "$HOOKDIR" && - write_script "$HOOKDIR/success.sample" <<-\EOF && - echo $0 >>actual_hooks - exit 0 - EOF - write_script "$HOOKDIR/fail.sample" <<-\EOF && - echo $0 >>actual_hooks - exit 1 - EOF - write_script "$HOOKDIR/non-exec.sample" <<-\EOF && - echo $0 >>actual_hooks - exit 1 - EOF - chmod -x "$HOOKDIR/non-exec.sample" && - write_script "$HOOKDIR/require-prefix.sample" <<-\EOF && - echo $0 >>actual_hooks - test $GIT_PREFIX = "success/" - EOF - write_script "$HOOKDIR/check-author.sample" <<-\EOF - echo $0 >>actual_hooks - test "$GIT_AUTHOR_NAME" = "New Author" && - test "$GIT_AUTHOR_EMAIL" = "newauthor@example.com" - EOF -' - test_expect_success 'root commit' ' echo "root" >file && git add file && @@ -96,10 +65,16 @@ test_expect_success '--no-verify with no hook (merge)' ' test_path_is_missing actual_hooks ' +setup_success_hook () { + test_when_finished "rm -f actual_hooks expected_hooks" && + echo "$1" >expected_hooks && + test_hook "$1" <<-EOF + echo $1 >>actual_hooks + EOF +} + test_expect_success 'with succeeding hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" expected_hooks actual_hooks" && - cp "$HOOKDIR/success.sample" "$PRECOMMIT" && - echo "$PRECOMMIT" >expected_hooks && + setup_success_hook "pre-commit" && echo "more" >>file && git add file && git commit -m "more" && @@ -107,9 +82,7 @@ test_expect_success 'with succeeding hook' ' ' test_expect_success 'with succeeding hook (merge)' ' - test_when_finished "rm -f \"$PREMERGE\" expected_hooks actual_hooks" && - cp "$HOOKDIR/success.sample" "$PREMERGE" && - echo "$PREMERGE" >expected_hooks && + setup_success_hook "pre-merge-commit" && git checkout side && git merge -m "merge main" main && git checkout main && @@ -117,17 +90,14 @@ test_expect_success 'with succeeding hook (merge)' ' ' test_expect_success 'automatic merge fails; both hooks are available' ' - test_when_finished "rm -f \"$PREMERGE\" \"$PRECOMMIT\"" && - test_when_finished "rm -f expected_hooks actual_hooks" && - test_when_finished "git checkout main" && - cp "$HOOKDIR/success.sample" "$PREMERGE" && - cp "$HOOKDIR/success.sample" "$PRECOMMIT" && + setup_success_hook "pre-commit" && + setup_success_hook "pre-merge-commit" && git checkout conflicting-a && test_must_fail git merge -m "merge conflicting-b" conflicting-b && test_path_is_missing actual_hooks && - echo "$PRECOMMIT" >expected_hooks && + echo "pre-commit" >expected_hooks && echo a+b >conflicting && git add conflicting && git commit -m "resolve conflict" && @@ -135,8 +105,7 @@ test_expect_success 'automatic merge fails; both hooks are available' ' ' test_expect_success '--no-verify with succeeding hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" actual_hooks" && - cp "$HOOKDIR/success.sample" "$PRECOMMIT" && + setup_success_hook "pre-commit" && echo "even more" >>file && git add file && git commit --no-verify -m "even more" && @@ -144,8 +113,7 @@ test_expect_success '--no-verify with succeeding hook' ' ' test_expect_success '--no-verify with succeeding hook (merge)' ' - test_when_finished "rm -f \"$PREMERGE\" actual_hooks" && - cp "$HOOKDIR/success.sample" "$PREMERGE" && + setup_success_hook "pre-merge-commit" && git branch -f side side-orig && git checkout side && git merge --no-verify -m "merge main" main && @@ -153,10 +121,19 @@ test_expect_success '--no-verify with succeeding hook (merge)' ' test_path_is_missing actual_hooks ' +setup_failing_hook () { + test_when_finished "rm -f actual_hooks" && + test_hook "$1" <<-EOF + echo $1-failing-hook >>actual_hooks + exit 1 + EOF +} + test_expect_success 'with failing hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" expected_hooks actual_hooks" && - cp "$HOOKDIR/fail.sample" "$PRECOMMIT" && - echo "$PRECOMMIT" >expected_hooks && + setup_failing_hook "pre-commit" && + test_when_finished "rm -f expected_hooks" && + echo "pre-commit-failing-hook" >expected_hooks && + echo "another" >>file && git add file && test_must_fail git commit -m "another" && @@ -164,8 +141,7 @@ test_expect_success 'with failing hook' ' ' test_expect_success '--no-verify with failing hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" actual_hooks" && - cp "$HOOKDIR/fail.sample" "$PRECOMMIT" && + setup_failing_hook "pre-commit" && echo "stuff" >>file && git add file && git commit --no-verify -m "stuff" && @@ -173,9 +149,8 @@ test_expect_success '--no-verify with failing hook' ' ' test_expect_success 'with failing hook (merge)' ' - test_when_finished "rm -f \"$PREMERGE\" expected_hooks actual_hooks" && - cp "$HOOKDIR/fail.sample" "$PREMERGE" && - echo "$PREMERGE" >expected_hooks && + setup_failing_hook "pre-merge-commit" && + echo "pre-merge-commit-failing-hook" >expected_hooks && git checkout side && test_must_fail git merge -m "merge main" main && git checkout main && @@ -183,8 +158,8 @@ test_expect_success 'with failing hook (merge)' ' ' test_expect_success '--no-verify with failing hook (merge)' ' - test_when_finished "rm -f \"$PREMERGE\" actual_hooks" && - cp "$HOOKDIR/fail.sample" "$PREMERGE" && + setup_failing_hook "pre-merge-commit" && + git branch -f side side-orig && git checkout side && git merge --no-verify -m "merge main" main && @@ -192,9 +167,18 @@ test_expect_success '--no-verify with failing hook (merge)' ' test_path_is_missing actual_hooks ' +setup_non_exec_hook () { + test_when_finished "rm -f actual_hooks" && + test_hook "$1" <<-\EOF && + echo non-exec >>actual_hooks + exit 1 + EOF + test_hook --disable "$1" +} + + test_expect_success POSIXPERM 'with non-executable hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" actual_hooks" && - cp "$HOOKDIR/non-exec.sample" "$PRECOMMIT" && + setup_non_exec_hook "pre-commit" && echo "content" >>file && git add file && git commit -m "content" && @@ -202,8 +186,7 @@ test_expect_success POSIXPERM 'with non-executable hook' ' ' test_expect_success POSIXPERM '--no-verify with non-executable hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" actual_hooks" && - cp "$HOOKDIR/non-exec.sample" "$PRECOMMIT" && + setup_non_exec_hook "pre-commit" && echo "more content" >>file && git add file && git commit --no-verify -m "more content" && @@ -211,8 +194,7 @@ test_expect_success POSIXPERM '--no-verify with non-executable hook' ' ' test_expect_success POSIXPERM 'with non-executable hook (merge)' ' - test_when_finished "rm -f \"$PREMERGE\" actual_hooks" && - cp "$HOOKDIR/non-exec.sample" "$PREMERGE" && + setup_non_exec_hook "pre-merge" && git branch -f side side-orig && git checkout side && git merge -m "merge main" main && @@ -221,8 +203,7 @@ test_expect_success POSIXPERM 'with non-executable hook (merge)' ' ' test_expect_success POSIXPERM '--no-verify with non-executable hook (merge)' ' - test_when_finished "rm -f \"$PREMERGE\" actual_hooks" && - cp "$HOOKDIR/non-exec.sample" "$PREMERGE" && + setup_non_exec_hook "pre-merge" && git branch -f side side-orig && git checkout side && git merge --no-verify -m "merge main" main && @@ -230,10 +211,18 @@ test_expect_success POSIXPERM '--no-verify with non-executable hook (merge)' ' test_path_is_missing actual_hooks ' +setup_require_prefix_hook () { + test_when_finished "rm -f expected_hooks" && + echo require-prefix >expected_hooks && + test_hook pre-commit <<-\EOF + echo require-prefix >>actual_hooks + test $GIT_PREFIX = "success/" + EOF +} + test_expect_success 'with hook requiring GIT_PREFIX' ' - test_when_finished "rm -rf \"$PRECOMMIT\" expected_hooks actual_hooks success" && - cp "$HOOKDIR/require-prefix.sample" "$PRECOMMIT" && - echo "$PRECOMMIT" >expected_hooks && + test_when_finished "rm -rf actual_hooks success" && + setup_require_prefix_hook && echo "more content" >>file && git add file && mkdir success && @@ -245,9 +234,8 @@ test_expect_success 'with hook requiring GIT_PREFIX' ' ' test_expect_success 'with failing hook requiring GIT_PREFIX' ' - test_when_finished "rm -rf \"$PRECOMMIT\" expected_hooks actual_hooks fail" && - cp "$HOOKDIR/require-prefix.sample" "$PRECOMMIT" && - echo "$PRECOMMIT" >expected_hooks && + test_when_finished "rm -rf actual_hooks fail" && + setup_require_prefix_hook && echo "more content" >>file && git add file && mkdir fail && @@ -259,13 +247,23 @@ test_expect_success 'with failing hook requiring GIT_PREFIX' ' test_cmp expected_hooks actual_hooks ' +setup_require_author_hook () { + test_when_finished "rm -f expected_hooks actual_hooks" && + echo check-author >expected_hooks && + test_hook pre-commit <<-\EOF + echo check-author >>actual_hooks + test "$GIT_AUTHOR_NAME" = "New Author" && + test "$GIT_AUTHOR_EMAIL" = "newauthor@example.com" + EOF +} + + test_expect_success 'check the author in hook' ' - test_when_finished "rm -f \"$PRECOMMIT\" expected_hooks actual_hooks" && - cp "$HOOKDIR/check-author.sample" "$PRECOMMIT" && + setup_require_author_hook && cat >expected_hooks <<-EOF && - $PRECOMMIT - $PRECOMMIT - $PRECOMMIT + check-author + check-author + check-author EOF test_must_fail git commit --allow-empty -m "by a.u.thor" && ( diff --git a/t/t7504-commit-msg-hook.sh b/t/t7504-commit-msg-hook.sh index bba58f0480..a39de8c112 100755 --- a/t/t7504-commit-msg-hook.sh +++ b/t/t7504-commit-msg-hook.sh @@ -54,15 +54,11 @@ test_expect_success '--no-verify with no hook (editor)' ' ' -# now install hook that always succeeds -HOOKDIR="$(git rev-parse --git-dir)/hooks" -HOOK="$HOOKDIR/commit-msg" -mkdir -p "$HOOKDIR" -cat > "$HOOK" <<EOF -#!/bin/sh -exit 0 -EOF -chmod +x "$HOOK" +test_expect_success 'setup: commit-msg hook that always succeeds' ' + test_hook --setup commit-msg <<-\EOF + exit 0 + EOF +' test_expect_success 'with succeeding hook' ' @@ -98,11 +94,11 @@ test_expect_success '--no-verify with succeeding hook (editor)' ' ' -# now a hook that fails -cat > "$HOOK" <<EOF -#!/bin/sh -exit 1 -EOF +test_expect_success 'setup: commit-msg hook that always fails' ' + test_hook --clobber commit-msg <<-\EOF + exit 1 + EOF +' commit_msg_is () { test "$(git log --pretty=format:%s%b -1)" = "$1" @@ -176,8 +172,12 @@ test_expect_success 'merge bypasses failing hook with --no-verify' ' commit_msg_is "Merge branch '\''main'\'' into newbranch" ' +test_expect_success 'setup: commit-msg hook made non-executable' ' + git_dir="$(git rev-parse --git-dir)" && + chmod -x "$git_dir/hooks/commit-msg" +' + -chmod -x "$HOOK" test_expect_success POSIXPERM 'with non-executable hook' ' echo "content" >file && @@ -212,13 +212,12 @@ test_expect_success POSIXPERM '--no-verify with non-executable hook (editor)' ' ' -# now a hook that edits the commit message -cat > "$HOOK" <<'EOF' -#!/bin/sh -echo "new message" > "$1" -exit 0 -EOF -chmod +x "$HOOK" +test_expect_success 'setup: commit-msg hook that edits the commit message' ' + test_hook --clobber commit-msg <<-\EOF + echo "new message" >"$1" + exit 0 + EOF +' test_expect_success 'hook edits commit message' ' diff --git a/t/t7505-prepare-commit-msg-hook.sh b/t/t7505-prepare-commit-msg-hook.sh index e39c809ca4..2128142a61 100755 --- a/t/t7505-prepare-commit-msg-hook.sh +++ b/t/t7505-prepare-commit-msg-hook.sh @@ -47,25 +47,19 @@ test_expect_success 'with no hook' ' ' -# set up fake editor for interactive editing -cat > fake-editor <<'EOF' -#!/bin/sh -exit 0 -EOF -chmod +x fake-editor - -## Not using test_set_editor here so we can easily ensure the editor variable -## is only set for the editor tests -FAKE_EDITOR="$(pwd)/fake-editor" -export FAKE_EDITOR +test_expect_success 'setup fake editor for interactive editing' ' + write_script fake-editor <<-\EOF && + exit 0 + EOF -# now install hook that always succeeds and adds a message -HOOKDIR="$(git rev-parse --git-dir)/hooks" -HOOK="$HOOKDIR/prepare-commit-msg" -mkdir -p "$HOOKDIR" -echo "#!$SHELL_PATH" > "$HOOK" -cat >> "$HOOK" <<'EOF' + ## Not using test_set_editor here so we can easily ensure the editor variable + ## is only set for the editor tests + FAKE_EDITOR="$(pwd)/fake-editor" && + export FAKE_EDITOR +' +test_expect_success 'setup prepare-commit-msg hook' ' + test_hook --setup prepare-commit-msg <<\EOF GIT_DIR=$(git rev-parse --git-dir) if test -d "$GIT_DIR/rebase-merge" then @@ -103,7 +97,7 @@ else fi exit 0 EOF -chmod +x "$HOOK" +' echo dummy template > "$(git rev-parse --git-dir)/template" @@ -265,10 +259,11 @@ test_expect_success 'with hook and editor (cherry-pick)' ' test "$(git log -1 --pretty=format:%s)" = merge ' -cat > "$HOOK" <<'EOF' -#!/bin/sh -exit 1 -EOF +test_expect_success 'setup: commit-msg hook that always fails' ' + test_hook --setup --clobber prepare-commit-msg <<-\EOF + exit 1 + EOF +' test_expect_success 'with failing hook' ' @@ -296,9 +291,9 @@ test_expect_success 'with failing hook (merge)' ' git checkout -B other HEAD@{1} && echo "more" >> file && git add file && - rm -f "$HOOK" && + test_hook --remove prepare-commit-msg && git commit -m other && - write_script "$HOOK" <<-EOF && + test_hook --setup prepare-commit-msg <<-\EOF && exit 1 EOF git checkout - && diff --git a/t/t7519-status-fsmonitor.sh b/t/t7519-status-fsmonitor.sh index fffc57120d..d4f9c6a837 100755 --- a/t/t7519-status-fsmonitor.sh +++ b/t/t7519-status-fsmonitor.sh @@ -26,7 +26,7 @@ dirty_repo () { } write_integration_script () { - write_script .git/hooks/fsmonitor-test<<-\EOF + test_hook --setup --clobber fsmonitor-test<<-\EOF if test "$#" -ne 2 then echo "$0: exactly 2 arguments expected" @@ -56,7 +56,6 @@ test_lazy_prereq UNTRACKED_CACHE ' ' test_expect_success 'setup' ' - mkdir -p .git/hooks && : >tracked && : >modified && mkdir dir1 && @@ -108,7 +107,7 @@ EOF # test that "update-index --fsmonitor-valid" sets the fsmonitor valid bit test_expect_success 'update-index --fsmonitor-valid" sets the fsmonitor valid bit' ' - write_script .git/hooks/fsmonitor-test<<-\EOF && + test_hook fsmonitor-test<<-\EOF && printf "last_update_token\0" EOF git update-index --fsmonitor && @@ -169,7 +168,7 @@ EOF # test that newly added files are marked valid test_expect_success 'newly added files are marked valid' ' - write_script .git/hooks/fsmonitor-test<<-\EOF && + test_hook --setup --clobber fsmonitor-test<<-\EOF && printf "last_update_token\0" EOF git add new && @@ -210,7 +209,7 @@ EOF # test that *only* files returned by the integration script get flagged as invalid test_expect_success '*only* files returned by the integration script get flagged as invalid' ' - write_script .git/hooks/fsmonitor-test<<-\EOF && + test_hook --clobber fsmonitor-test<<-\EOF && printf "last_update_token\0" printf "dir1/modified\0" EOF @@ -231,7 +230,7 @@ test_expect_success 'refresh_index() invalidates fsmonitor cache' ' dirty_repo && write_integration_script && git add . && - write_script .git/hooks/fsmonitor-test<<-\EOF && + test_hook --clobber fsmonitor-test<<-\EOF && EOF git commit -m "to reset" && git reset HEAD~1 && @@ -280,7 +279,7 @@ do # Make sure it's actually skipping the check for modified and untracked # (if enabled) files unless it is told about them. test_expect_success "status doesn't detect unreported modifications" ' - write_script .git/hooks/fsmonitor-test<<-\EOF && + test_hook --clobber fsmonitor-test<<-\EOF && printf "last_update_token\0" :>marker EOF @@ -322,7 +321,6 @@ test_expect_success UNTRACKED_CACHE 'ignore .git changes when invalidating UNTR' test_create_repo dot-git && ( cd dot-git && - mkdir -p .git/hooks && : >tracked && test-tool chmtime =-60 tracked && : >modified && @@ -414,14 +412,14 @@ test_expect_success 'status succeeds with sparse index' ' git -C sparse sparse-checkout init --cone --sparse-index && git -C sparse sparse-checkout set dir1 dir2 && - write_script .git/hooks/fsmonitor-test <<-\EOF && + test_hook --clobber fsmonitor-test <<-\EOF && printf "last_update_token\0" EOF git -C full config core.fsmonitor ../.git/hooks/fsmonitor-test && git -C sparse config core.fsmonitor ../.git/hooks/fsmonitor-test && check_sparse_index_behavior ! && - write_script .git/hooks/fsmonitor-test <<-\EOF && + test_hook --clobber fsmonitor-test <<-\EOF && printf "last_update_token\0" printf "dir1/modified\0" EOF @@ -439,7 +437,7 @@ test_expect_success 'status succeeds with sparse index' ' # This one modifies outside the sparse-checkout definition # and hence we expect to expand the sparse-index. - write_script .git/hooks/fsmonitor-test <<-\EOF && + test_hook --clobber fsmonitor-test <<-\EOF && printf "last_update_token\0" printf "dir1a/modified\0" EOF diff --git a/t/t7520-ignored-hook-warning.sh b/t/t7520-ignored-hook-warning.sh index 634fb7f23a..dc57526e6f 100755 --- a/t/t7520-ignored-hook-warning.sh +++ b/t/t7520-ignored-hook-warning.sh @@ -5,10 +5,7 @@ test_description='ignored hook warning' . ./test-lib.sh test_expect_success setup ' - hookdir="$(git rev-parse --git-dir)/hooks" && - hook="$hookdir/pre-commit" && - mkdir -p "$hookdir" && - write_script "$hook" <<-\EOF + test_hook --setup pre-commit <<-\EOF exit 0 EOF ' @@ -19,20 +16,20 @@ test_expect_success 'no warning if hook is not ignored' ' ' test_expect_success POSIXPERM 'warning if hook is ignored' ' - chmod -x "$hook" && + test_hook --disable pre-commit && git commit --allow-empty -m "even more" 2>message && test_i18ngrep -e "hook was ignored" message ' test_expect_success POSIXPERM 'no warning if advice.ignoredHook set to false' ' test_config advice.ignoredHook false && - chmod -x "$hook" && + test_hook --disable pre-commit && git commit --allow-empty -m "even more" 2>message && test_i18ngrep ! -e "hook was ignored" message ' test_expect_success 'no warning if unset advice.ignoredHook and hook removed' ' - rm -f "$hook" && + test_hook --remove pre-commit && test_unconfig advice.ignoredHook && git commit --allow-empty -m "even more" 2>message && test_i18ngrep ! -e "hook was ignored" message diff --git a/t/t7700-repack.sh b/t/t7700-repack.sh index 5922fb5bdd..770d143204 100755 --- a/t/t7700-repack.sh +++ b/t/t7700-repack.sh @@ -381,4 +381,54 @@ test_expect_success TTY '--quiet disables progress' ' test_must_be_empty stderr ' +test_expect_success 'setup for update-server-info' ' + git init update-server-info && + test_commit -C update-server-info message +' + +test_server_info_present () { + test_path_is_file update-server-info/.git/objects/info/packs && + test_path_is_file update-server-info/.git/info/refs +} + +test_server_info_missing () { + test_path_is_missing update-server-info/.git/objects/info/packs && + test_path_is_missing update-server-info/.git/info/refs +} + +test_server_info_cleanup () { + rm -f update-server-info/.git/objects/info/packs update-server-info/.git/info/refs && + test_server_info_missing +} + +test_expect_success 'updates server info by default' ' + test_server_info_cleanup && + git -C update-server-info repack && + test_server_info_present +' + +test_expect_success '-n skips updating server info' ' + test_server_info_cleanup && + git -C update-server-info repack -n && + test_server_info_missing +' + +test_expect_success 'repack.updateServerInfo=true updates server info' ' + test_server_info_cleanup && + git -C update-server-info -c repack.updateServerInfo=true repack && + test_server_info_present +' + +test_expect_success 'repack.updateServerInfo=false skips updating server info' ' + test_server_info_cleanup && + git -C update-server-info -c repack.updateServerInfo=false repack && + test_server_info_missing +' + +test_expect_success '-n overrides repack.updateServerInfo=true' ' + test_server_info_cleanup && + git -C update-server-info -c repack.updateServerInfo=true repack -n && + test_server_info_missing +' + test_done diff --git a/t/t9001-send-email.sh b/t/t9001-send-email.sh index 84d0f40d76..42694fe584 100755 --- a/t/t9001-send-email.sh +++ b/t/t9001-send-email.sh @@ -2288,9 +2288,7 @@ test_expect_success $PREREQ 'cmdline in-reply-to used with --no-thread' ' ' test_expect_success $PREREQ 'invoke hook' ' - mkdir -p .git/hooks && - - write_script .git/hooks/sendemail-validate <<-\EOF && + test_hook sendemail-validate <<-\EOF && # test that we have the correct environment variable, pwd, and # argument case "$GIT_DIR" in diff --git a/t/t9800-git-p4-basic.sh b/t/t9800-git-p4-basic.sh index 806005a793..8b30062c0c 100755 --- a/t/t9800-git-p4-basic.sh +++ b/t/t9800-git-p4-basic.sh @@ -277,16 +277,21 @@ test_expect_success 'run hook p4-pre-submit before submit' ' git commit -m "add hello.txt" && git config git-p4.skipSubmitEdit true && git p4 submit --dry-run >out && - grep "Would apply" out && - mkdir -p .git/hooks && - write_script .git/hooks/p4-pre-submit <<-\EOF && - exit 0 - EOF + grep "Would apply" out + ) && + test_hook -C "$git" p4-pre-submit <<-\EOF && + exit 0 + EOF + ( + cd "$git" && git p4 submit --dry-run >out && - grep "Would apply" out && - write_script .git/hooks/p4-pre-submit <<-\EOF && - exit 1 - EOF + grep "Would apply" out + ) && + test_hook -C "$git" --clobber p4-pre-submit <<-\EOF && + exit 1 + EOF + ( + cd "$git" && test_must_fail git p4 submit --dry-run >errs 2>&1 && ! grep "Would apply" errs ) diff --git a/t/test-lib-functions.sh b/t/test-lib-functions.sh index 0f439c99d6..1c3d65e6ea 100644 --- a/t/test-lib-functions.sh +++ b/t/test-lib-functions.sh @@ -329,7 +329,7 @@ test_commit () { else $echo "${3-$1}" >"$indir$file" fi && - git ${indir:+ -C "$indir"} add "$file" && + git ${indir:+ -C "$indir"} add -- "$file" && if test -z "$notick" then test_tick @@ -551,6 +551,82 @@ write_script () { chmod +x "$1" } +# Usage: test_hook [options] <hook-name> <<-\EOF +# +# -C <dir>: +# Run all git commands in directory <dir> +# --setup +# Setup a hook for subsequent tests, i.e. don't remove it in a +# "test_when_finished" +# --clobber +# Overwrite an existing <hook-name>, if it exists. Implies +# --setup (i.e. the "test_when_finished" is assumed to have been +# set up already). +# --disable +# Disable (chmod -x) an existing <hook-name>, which must exist. +# --remove +# Remove (rm -f) an existing <hook-name>, which must exist. +test_hook () { + setup= && + clobber= && + disable= && + remove= && + indir= && + while test $# != 0 + do + case "$1" in + -C) + indir="$2" && + shift + ;; + --setup) + setup=t + ;; + --clobber) + clobber=t + ;; + --disable) + disable=t + ;; + --remove) + remove=t + ;; + -*) + BUG "invalid argument: $1" + ;; + *) + break + ;; + esac && + shift + done && + + git_dir=$(git -C "$indir" rev-parse --absolute-git-dir) && + hook_dir="$git_dir/hooks" && + hook_file="$hook_dir/$1" && + if test -n "$disable$remove" + then + test_path_is_file "$hook_file" && + if test -n "$disable" + then + chmod -x "$hook_file" + elif test -n "$remove" + then + rm -f "$hook_file" + fi && + return 0 + fi && + if test -z "$clobber" + then + test_path_is_missing "$hook_file" + fi && + if test -z "$setup$clobber" + then + test_when_finished "rm \"$hook_file\"" + fi && + write_script "$hook_file" +} + # Use test_set_prereq to tell that a particular prerequisite is available. # The prerequisite can later be checked for in two ways: # diff --git a/t/test-lib.sh b/t/test-lib.sh index 515b1af7ed..4373f7d70b 100644 --- a/t/test-lib.sh +++ b/t/test-lib.sh @@ -806,7 +806,11 @@ test_failure_ () { say_color error "not ok $test_count - $1" shift printf '%s\n' "$*" | sed -e 's/^/# /' - test "$immediate" = "" || _error_exit + if test -n "$immediate" + then + say_color error "1..$test_count" + _error_exit + fi } test_known_broken_ok_ () { |