diff mbox series

[v4,28/29] blame: emit a better error on 'git blame directory'

Message ID 81da54902217891f8115cbad9194c88535615d65.1616282534.git.avarab@gmail.com (mailing list archive)
State New, archived
Headers show
Series tree-walk: mostly replace "mode" with "enum object_type" | expand

Commit Message

Ævar Arnfjörð Bjarmason March 21, 2021, 12:01 a.m. UTC
Change an early check for non-blobs in verify_working_tree_path() to
let any such objects pass, and instead die shortly thereafter in the
fake_working_tree_commit() caller's type check.

Now e.g. doing "git blame t" in git.git emits:

    fatal: unsupported file type t

Instead of:

    fatal: no such path 't' in HEAD

The main point of this test is to assert that we're not doing
something uniquely bad when in a conflicted merge. See
cd8ae20195 (git-blame shouldn't crash if run in an unmerged tree,
2007-10-18) and 9aeaab6811 (blame: allow "blame file" in the middle of
a conflicted merge, 2012-09-11) for the bug the t8004 test was
originally meant to address.

But when extending it let's grep out the specific error message for
good measure. Having to change it in the future (e.g. as part of my
parallel series to improve such 'OID does not match type' messages) is
a small price for ensuring it doesn't regress.

Signed-off-by: Ævar Arnfjörð Bjarmason <avarab@gmail.com>
---
 blame.c                         |  8 ++------
 t/t8004-blame-with-conflicts.sh | 21 +++++++++++++++++++++
 2 files changed, 23 insertions(+), 6 deletions(-)
diff mbox series

Patch

diff --git a/blame.c b/blame.c
index 13825b86e65..3c3cb2f8f96 100644
--- a/blame.c
+++ b/blame.c
@@ -100,12 +100,8 @@  static void verify_working_tree_path(struct repository *r,
 
 	for (parents = work_tree->parents; parents; parents = parents->next) {
 		const struct object_id *commit_oid = &parents->item->object.oid;
-		struct object_id blob_oid;
-		unsigned short mode;
-		int ret = get_tree_entry_mode(r, commit_oid, path, &blob_oid,
-					      &mode);
-
-		if (!ret && oid_object_info(r, &blob_oid, NULL) == OBJ_BLOB)
+		struct object_id oid;
+		if (!get_tree_entry_path(r, commit_oid, path, &oid))
 			return;
 	}
 
diff --git a/t/t8004-blame-with-conflicts.sh b/t/t8004-blame-with-conflicts.sh
index 35414a53363..5e3dea35a50 100755
--- a/t/t8004-blame-with-conflicts.sh
+++ b/t/t8004-blame-with-conflicts.sh
@@ -73,4 +73,25 @@  test_expect_success 'blame does not crash with conflicted file in stages 1,3' '
 	git blame file1
 '
 
+test_expect_success 'setup second case' '
+	git merge --abort
+'
+
+test_expect_success 'blame on directory/file conflict' '
+	mkdir d &&
+	test_commit second &&
+	test_commit d/file &&
+	test_must_fail git blame d 2>expected &&
+	grep "unsupported file type d" expected &&
+
+	git reset --hard second &&
+	>d &&
+	git add d &&
+	git commit -m"a not-a-dir" &&
+	test_must_fail git merge d/file &&
+
+	test_must_fail git blame d 2>actual &&
+	test_cmp expected actual
+'
+
 test_done