builtin/cat-file: mark 'git cat-file' sparse-index compatible

This change affects how 'git cat-file' works with the index when specifying an object with the ":<path>" syntax (which will give file contents from the index). 'git cat-file' expands a sparse index to a full index any time contents are requested from the index by specifying an object with the ":<path>" syntax. This is true even when the requested file is part of the sparse index, and results in much slower 'git cat-file' operations when working within the sparse index. Mark 'git cat-file' as not needing a full index, so that you only pay the cost of expanding the sparse index to a full index when you request a file outside of the sparse index. Add tests to ensure both that: - 'git cat-file' returns the correct file contents whether or not the file is in the sparse index - 'git cat-file' expands to the full index any time you request something outside of the sparse index Signed-off-by: Kevin Lyles <klyles+github@epic.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Kevin Lyles committed Sep 3, 2024 at 22:06 UTC e65b0c7c36683a8634b345af1cc3dc7676b3904a
2 files changed +39
builtin/cat-file.c
+3
@@ -1047,6 +1047,9 @@ int cmd_cat_file(int argc, const char **argv, const char *prefix)
1047 if (batch.buffer_output < 0)
1048 batch.buffer_output = batch.all_objects;
1049
1050 + prepare_repo_settings(the_repository);
1051 + the_repository->settings.command_requires_full_index = 0;
1052 +
1053 /* Return early if we're in batch mode? */
1054 if (batch.enabled) {
1055 if (opt_cw)
t/t1092-sparse-checkout-compatibility.sh
+36
@@ -2358,4 +2358,40 @@ test_expect_success 'advice.sparseIndexExpanded' '
2358 grep "The sparse index is expanding to a full index" err
2359 '
2360
2361 +test_expect_success 'cat-file -p' '
2362 + init_repos &&
2363 + echo "new content" >>full-checkout/deep/a &&
2364 + echo "new content" >>sparse-checkout/deep/a &&
2365 + echo "new content" >>sparse-index/deep/a &&
2366 + run_on_all git add deep/a &&
2367 +
2368 + test_all_match git cat-file -p :deep/a &&
2369 + ensure_not_expanded cat-file -p :deep/a &&
2370 + test_all_match git cat-file -p :folder1/a &&
2371 + ensure_expanded cat-file -p :folder1/a
2372 +'
2373 +
2374 +test_expect_success 'cat-file --batch' '
2375 + init_repos &&
2376 + echo "new content" >>full-checkout/deep/a &&
2377 + echo "new content" >>sparse-checkout/deep/a &&
2378 + echo "new content" >>sparse-index/deep/a &&
2379 + run_on_all git add deep/a &&
2380 +
2381 + echo ":deep/a" >in &&
2382 + test_all_match git cat-file --batch <in &&
2383 + ensure_not_expanded cat-file --batch <in &&
2384 +
2385 + echo ":folder1/a" >in &&
2386 + test_all_match git cat-file --batch <in &&
2387 + ensure_expanded cat-file --batch <in &&
2388 +
2389 + cat >in <<-\EOF &&
2390 + :deep/a
2391 + :folder1/a
2392 + EOF
2393 + test_all_match git cat-file --batch <in &&
2394 + ensure_expanded cat-file --batch <in
2395 +'
2396 +
2397 test_done