t/helper: add 'find-pack' test-tool

In a following commit, we will make it possible to separate objects in different packfiles depending on a filter. To make sure that the right objects are in the right packs, let's add a new test-tool that can display which packfile(s) a given object is in. Let's also make it possible to check if a given object is in the expected number of packfiles with a `--check-count <n>` option. Signed-off-by: Christian Couder <chriscool@tuxfamily.org> Signed-off-by: Junio C Hamano <gitster@pobox.com>

Christian Couder committed Oct 2, 2023 at 18:54 UTC 66589f89ab8bf19f79fa9e9ec156bce43ed70e53
5 files changed +135
Makefile
+1
@@ -800,6 +800,7 @@ TEST_BUILTINS_OBJS += test-dump-untracked-cache.o
800 TEST_BUILTINS_OBJS += test-env-helper.o
801 TEST_BUILTINS_OBJS += test-example-decorate.o
802 TEST_BUILTINS_OBJS += test-fast-rebase.o
803 +TEST_BUILTINS_OBJS += test-find-pack.o
804 TEST_BUILTINS_OBJS += test-fsmonitor-client.o
805 TEST_BUILTINS_OBJS += test-genrandom.o
806 TEST_BUILTINS_OBJS += test-genzeros.o
t/helper/test-find-pack.c new
+50
@@ -0,0 +1,50 @@
1 +#include "test-tool.h"
2 +#include "object-name.h"
3 +#include "object-store.h"
4 +#include "packfile.h"
5 +#include "parse-options.h"
6 +#include "setup.h"
7 +
8 +/*
9 + * Display the path(s), one per line, of the packfile(s) containing
10 + * the given object.
11 + *
12 + * If '--check-count <n>' is passed, then error out if the number of
13 + * packfiles containing the object is not <n>.
14 + */
15 +
16 +static const char *find_pack_usage[] = {
17 + "test-tool find-pack [--check-count <n>] <object>",
18 + NULL
19 +};
20 +
21 +int cmd__find_pack(int argc, const char **argv)
22 +{
23 + struct object_id oid;
24 + struct packed_git *p;
25 + int count = -1, actual_count = 0;
26 + const char *prefix = setup_git_directory();
27 +
28 + struct option options[] = {
29 + OPT_INTEGER('c', "check-count", &count, "expected number of packs"),
30 + OPT_END(),
31 + };
32 +
33 + argc = parse_options(argc, argv, prefix, options, find_pack_usage, 0);
34 + if (argc != 1)
35 + usage(find_pack_usage[0]);
36 +
37 + if (repo_get_oid(the_repository, argv[0], &oid))
38 + die("cannot parse %s as an object name", argv[0]);
39 +
40 + for (p = get_all_packs(the_repository); p; p = p->next)
41 + if (find_pack_entry_one(oid.hash, p)) {
42 + printf("%s\n", p->pack_name);
43 + actual_count++;
44 + }
45 +
46 + if (count > -1 && count != actual_count)
47 + die("bad packfile count %d instead of %d", actual_count, count);
48 +
49 + return 0;
50 +}
t/helper/test-tool.c
+1
@@ -31,6 +31,7 @@ static struct test_cmd cmds[] = {
31 { "env-helper", cmd__env_helper },
32 { "example-decorate", cmd__example_decorate },
33 { "fast-rebase", cmd__fast_rebase },
34 + { "find-pack", cmd__find_pack },
35 { "fsmonitor-client", cmd__fsmonitor_client },
36 { "genrandom", cmd__genrandom },
37 { "genzeros", cmd__genzeros },
t/helper/test-tool.h
+1
@@ -25,6 +25,7 @@ int cmd__dump_reftable(int argc, const char **argv);
25 int cmd__env_helper(int argc, const char **argv);
26 int cmd__example_decorate(int argc, const char **argv);
27 int cmd__fast_rebase(int argc, const char **argv);
28 +int cmd__find_pack(int argc, const char **argv);
29 int cmd__fsmonitor_client(int argc, const char **argv);
30 int cmd__genrandom(int argc, const char **argv);
31 int cmd__genzeros(int argc, const char **argv);
t/t0081-find-pack.sh new
+82
@@ -0,0 +1,82 @@
1 +#!/bin/sh
2 +
3 +test_description='test `test-tool find-pack`'
4 +
5 +TEST_PASSES_SANITIZE_LEAK=true
6 +. ./test-lib.sh
7 +
8 +test_expect_success 'setup' '
9 + test_commit one &&
10 + test_commit two &&
11 + test_commit three &&
12 + test_commit four &&
13 + test_commit five
14 +'
15 +
16 +test_expect_success 'repack everything into a single packfile' '
17 + git repack -a -d --no-write-bitmap-index &&
18 +
19 + head_commit_pack=$(test-tool find-pack HEAD) &&
20 + head_tree_pack=$(test-tool find-pack HEAD^{tree}) &&
21 + one_pack=$(test-tool find-pack HEAD:one.t) &&
22 + three_pack=$(test-tool find-pack HEAD:three.t) &&
23 + old_commit_pack=$(test-tool find-pack HEAD~4) &&
24 +
25 + test-tool find-pack --check-count 1 HEAD &&
26 + test-tool find-pack --check-count=1 HEAD^{tree} &&
27 + ! test-tool find-pack --check-count=0 HEAD:one.t &&
28 + ! test-tool find-pack -c 2 HEAD:one.t &&
29 + test-tool find-pack -c 1 HEAD:three.t &&
30 +
31 + # Packfile exists at the right path
32 + case "$head_commit_pack" in
33 + ".git/objects/pack/pack-"*".pack") true ;;
34 + *) false ;;
35 + esac &&
36 + test -f "$head_commit_pack" &&
37 +
38 + # Everything is in the same pack
39 + test "$head_commit_pack" = "$head_tree_pack" &&
40 + test "$head_commit_pack" = "$one_pack" &&
41 + test "$head_commit_pack" = "$three_pack" &&
42 + test "$head_commit_pack" = "$old_commit_pack"
43 +'
44 +
45 +test_expect_success 'add more packfiles' '
46 + git rev-parse HEAD^{tree} HEAD:two.t HEAD:four.t >objects &&
47 + git pack-objects .git/objects/pack/mypackname1 >packhash1 <objects &&
48 +
49 + git rev-parse HEAD~ HEAD~^{tree} HEAD:five.t >objects &&
50 + git pack-objects .git/objects/pack/mypackname2 >packhash2 <objects &&
51 +
52 + head_commit_pack=$(test-tool find-pack HEAD) &&
53 +
54 + # HEAD^{tree} is in 2 packfiles
55 + test-tool find-pack HEAD^{tree} >head_tree_packs &&
56 + grep "$head_commit_pack" head_tree_packs &&
57 + grep mypackname1 head_tree_packs &&
58 + ! grep mypackname2 head_tree_packs &&
59 + test-tool find-pack --check-count 2 HEAD^{tree} &&
60 + ! test-tool find-pack --check-count 1 HEAD^{tree} &&
61 +
62 + # HEAD:five.t is also in 2 packfiles
63 + test-tool find-pack HEAD:five.t >five_packs &&
64 + grep "$head_commit_pack" five_packs &&
65 + ! grep mypackname1 five_packs &&
66 + grep mypackname2 five_packs &&
67 + test-tool find-pack -c 2 HEAD:five.t &&
68 + ! test-tool find-pack --check-count=0 HEAD:five.t
69 +'
70 +
71 +test_expect_success 'add more commits (as loose objects)' '
72 + test_commit six &&
73 + test_commit seven &&
74 +
75 + test -z "$(test-tool find-pack HEAD)" &&
76 + test -z "$(test-tool find-pack HEAD:six.t)" &&
77 + test-tool find-pack --check-count 0 HEAD &&
78 + test-tool find-pack -c 0 HEAD:six.t &&
79 + ! test-tool find-pack -c 1 HEAD:seven.t
80 +'
81 +
82 +test_done