From: Pushkar Singh Date: Thu, 15 Jan 2026 17:52:26 +0000 (+0000) Subject: subtree: validate --prefix against commit in split X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=d09107e43996d9ea558a07047f71e80737c90556;p=thirdparty%2Fgit.git subtree: validate --prefix against commit in split git subtree split currently validates --prefix against the working tree. This breaks when splitting an older commit or when the working tree does not contain the subtree, even though the commit does. For example: git subtree split --prefix=pkg fails if pkg was removed later, even though it exists in . Fix this by validating the prefix against the specified commit using git ls-tree instead of the working tree. Add a test to ensure this behavior does not regress. Signed-off-by: Pushkar Singh Signed-off-by: Junio C Hamano --- diff --git a/contrib/subtree/git-subtree.sh b/contrib/subtree/git-subtree.sh index 17106d1a72..324ed38148 100755 --- a/contrib/subtree/git-subtree.sh +++ b/contrib/subtree/git-subtree.sh @@ -257,6 +257,9 @@ main () { test -e "$arg_prefix" && die "fatal: prefix '$arg_prefix' already exists." ;; + split) + # checked later against the commit, not the working tree + ;; *) test -e "$arg_prefix" || die "fatal: '$arg_prefix' does not exist; use 'git subtree add'" @@ -966,6 +969,12 @@ cmd_split () { else die "fatal: you must provide exactly one revision, and optionally a repository. Got: '$*'" fi + + # Now validate prefix against the commit, not the working tree + if ! git ls-tree -d "$rev" -- "$dir" >/dev/null + then + die "fatal: '$dir' does not exist in commit $rev" + fi repository="" if test "$#" = 2 then diff --git a/contrib/subtree/t/t7900-subtree.sh b/contrib/subtree/t/t7900-subtree.sh index 316dc5269e..e4f632f3af 100755 --- a/contrib/subtree/t/t7900-subtree.sh +++ b/contrib/subtree/t/t7900-subtree.sh @@ -368,6 +368,28 @@ test_expect_success 'split requires path given by option --prefix must exist' ' ) ' +test_expect_success 'split works when prefix exists in commit but not in working tree' ' + subtree_test_create_repo "$test_count" && + ( + cd "$test_count" && + + # create subtree + mkdir pkg && + echo ok >pkg/file && + git add pkg && + git commit -m "add pkg" && + good=$(git rev-parse HEAD) && + + # remove it from working tree in later commit + git rm -r pkg && + git commit -m "remove pkg" && + + # must still be able to split using the old commit + git subtree split --prefix=pkg "$good" >out && + test -s out + ) +' + test_expect_success 'split rejects flags for add' ' subtree_test_create_repo "$test_count" && subtree_test_create_repo "$test_count/sub proj" &&