t/helper: add test-ref-store to test ref-store functions
Signed-off-by: Nguyễn Thái Ngọc Duy <pclouds@gmail.com> Signed-off-by: Junio C Hamano <gitster@pobox.com>
Nguyễn Thái Ngọc Duy committed
Mar 26, 2017 at 09:42 UTC
80f2a6097c403234892b884a21810411e5837853
3 files changed
+279
Makefile
+1
@@ -622,6 +622,7 @@ TEST_PROGRAMS_NEED_X += test-parse-options
622
TEST_PROGRAMS_NEED_X += test-path-utils
623
TEST_PROGRAMS_NEED_X += test-prio-queue
624
TEST_PROGRAMS_NEED_X += test-read-cache
625
+TEST_PROGRAMS_NEED_X += test-ref-store
626
TEST_PROGRAMS_NEED_X += test-regex
627
TEST_PROGRAMS_NEED_X += test-revision-walking
628
TEST_PROGRAMS_NEED_X += test-run-command
t/helper/.gitignore
+1
@@ -19,6 +19,7 @@
19
/test-path-utils
20
/test-prio-queue
21
/test-read-cache
22
+/test-ref-store
23
/test-regex
24
/test-revision-walking
25
/test-run-command
t/helper/test-ref-store.c
new
+277
@@ -0,0 +1,277 @@
1
+#include "cache.h"
2
+#include "refs.h"
3
+
4
+static const char *notnull(const char *arg, const char *name)
5
+{
6
+ if (!arg)
7
+ die("%s required", name);
8
+ return arg;
9
+}
10
+
11
+static unsigned int arg_flags(const char *arg, const char *name)
12
+{
13
+ return atoi(notnull(arg, name));
14
+}
15
+
16
+static const char **get_store(const char **argv, struct ref_store **refs)
17
+{
18
+ const char *gitdir;
19
+
20
+ if (!argv[0]) {
21
+ die("ref store required");
22
+ } else if (!strcmp(argv[0], "main")) {
23
+ *refs = get_main_ref_store();
24
+ } else if (skip_prefix(argv[0], "submodule:", &gitdir)) {
25
+ struct strbuf sb = STRBUF_INIT;
26
+ int ret;
27
+
28
+ ret = strbuf_git_path_submodule(&sb, gitdir, "objects/");
29
+ if (ret)
30
+ die("strbuf_git_path_submodule failed: %d", ret);
31
+ add_to_alternates_memory(sb.buf);
32
+ strbuf_release(&sb);
33
+
34
+ *refs = get_submodule_ref_store(gitdir);
35
+ } else
36
+ die("unknown backend %s", argv[0]);
37
+
38
+ if (!*refs)
39
+ die("no ref store");
40
+
41
+ /* consume store-specific optional arguments if needed */
42
+
43
+ return argv + 1;
44
+}
45
+
46
+
47
+static int cmd_pack_refs(struct ref_store *refs, const char **argv)
48
+{
49
+ unsigned int flags = arg_flags(*argv++, "flags");
50
+
51
+ return refs_pack_refs(refs, flags);
52
+}
53
+
54
+static int cmd_peel_ref(struct ref_store *refs, const char **argv)
55
+{
56
+ const char *refname = notnull(*argv++, "refname");
57
+ unsigned char sha1[20];
58
+ int ret;
59
+
60
+ ret = refs_peel_ref(refs, refname, sha1);
61
+ if (!ret)
62
+ puts(sha1_to_hex(sha1));
63
+ return ret;
64
+}
65
+
66
+static int cmd_create_symref(struct ref_store *refs, const char **argv)
67
+{
68
+ const char *refname = notnull(*argv++, "refname");
69
+ const char *target = notnull(*argv++, "target");
70
+ const char *logmsg = *argv++;
71
+
72
+ return refs_create_symref(refs, refname, target, logmsg);
73
+}
74
+
75
+static int cmd_delete_refs(struct ref_store *refs, const char **argv)
76
+{
77
+ unsigned int flags = arg_flags(*argv++, "flags");
78
+ struct string_list refnames = STRING_LIST_INIT_NODUP;
79
+
80
+ while (*argv)
81
+ string_list_append(&refnames, *argv++);
82
+
83
+ return refs_delete_refs(refs, &refnames, flags);
84
+}
85
+
86
+static int cmd_rename_ref(struct ref_store *refs, const char **argv)
87
+{
88
+ const char *oldref = notnull(*argv++, "oldref");
89
+ const char *newref = notnull(*argv++, "newref");
90
+ const char *logmsg = *argv++;
91
+
92
+ return refs_rename_ref(refs, oldref, newref, logmsg);
93
+}
94
+
95
+static int each_ref(const char *refname, const struct object_id *oid,
96
+ int flags, void *cb_data)
97
+{
98
+ printf("%s %s 0x%x\n", oid_to_hex(oid), refname, flags);
99
+ return 0;
100
+}
101
+
102
+static int cmd_for_each_ref(struct ref_store *refs, const char **argv)
103
+{
104
+ const char *prefix = notnull(*argv++, "prefix");
105
+
106
+ return refs_for_each_ref_in(refs, prefix, each_ref, NULL);
107
+}
108
+
109
+static int cmd_resolve_ref(struct ref_store *refs, const char **argv)
110
+{
111
+ unsigned char sha1[20];
112
+ const char *refname = notnull(*argv++, "refname");
113
+ int resolve_flags = arg_flags(*argv++, "resolve-flags");
114
+ int flags;
115
+ const char *ref;
116
+
117
+ ref = refs_resolve_ref_unsafe(refs, refname, resolve_flags,
118
+ sha1, &flags);
119
+ printf("%s %s 0x%x\n", sha1_to_hex(sha1), ref, flags);
120
+ return ref ? 0 : 1;
121
+}
122
+
123
+static int cmd_verify_ref(struct ref_store *refs, const char **argv)
124
+{
125
+ const char *refname = notnull(*argv++, "refname");
126
+ struct strbuf err = STRBUF_INIT;
127
+ int ret;
128
+
129
+ ret = refs_verify_refname_available(refs, refname, NULL, NULL, &err);
130
+ if (err.len)
131
+ puts(err.buf);
132
+ return ret;
133
+}
134
+
135
+static int cmd_for_each_reflog(struct ref_store *refs, const char **argv)
136
+{
137
+ return refs_for_each_reflog(refs, each_ref, NULL);
138
+}
139
+
140
+static int each_reflog(struct object_id *old_oid, struct object_id *new_oid,
141
+ const char *committer, unsigned long timestamp,
142
+ int tz, const char *msg, void *cb_data)
143
+{
144
+ printf("%s %s %s %lu %d %s\n",
145
+ oid_to_hex(old_oid), oid_to_hex(new_oid),
146
+ committer, timestamp, tz, msg);
147
+ return 0;
148
+}
149
+
150
+static int cmd_for_each_reflog_ent(struct ref_store *refs, const char **argv)
151
+{
152
+ const char *refname = notnull(*argv++, "refname");
153
+
154
+ return refs_for_each_reflog_ent(refs, refname, each_reflog, refs);
155
+}
156
+
157
+static int cmd_for_each_reflog_ent_reverse(struct ref_store *refs, const char **argv)
158
+{
159
+ const char *refname = notnull(*argv++, "refname");
160
+
161
+ return refs_for_each_reflog_ent_reverse(refs, refname, each_reflog, refs);
162
+}
163
+
164
+static int cmd_reflog_exists(struct ref_store *refs, const char **argv)
165
+{
166
+ const char *refname = notnull(*argv++, "refname");
167
+
168
+ return !refs_reflog_exists(refs, refname);
169
+}
170
+
171
+static int cmd_create_reflog(struct ref_store *refs, const char **argv)
172
+{
173
+ const char *refname = notnull(*argv++, "refname");
174
+ int force_create = arg_flags(*argv++, "force-create");
175
+ struct strbuf err = STRBUF_INIT;
176
+ int ret;
177
+
178
+ ret = refs_create_reflog(refs, refname, force_create, &err);
179
+ if (err.len)
180
+ puts(err.buf);
181
+ return ret;
182
+}
183
+
184
+static int cmd_delete_reflog(struct ref_store *refs, const char **argv)
185
+{
186
+ const char *refname = notnull(*argv++, "refname");
187
+
188
+ return refs_delete_reflog(refs, refname);
189
+}
190
+
191
+static int cmd_reflog_expire(struct ref_store *refs, const char **argv)
192
+{
193
+ die("not supported yet");
194
+}
195
+
196
+static int cmd_delete_ref(struct ref_store *refs, const char **argv)
197
+{
198
+ const char *msg = notnull(*argv++, "msg");
199
+ const char *refname = notnull(*argv++, "refname");
200
+ const char *sha1_buf = notnull(*argv++, "old-sha1");
201
+ unsigned int flags = arg_flags(*argv++, "flags");
202
+ unsigned char old_sha1[20];
203
+
204
+ if (get_sha1_hex(sha1_buf, old_sha1))
205
+ die("not sha-1");
206
+
207
+ return refs_delete_ref(refs, msg, refname, old_sha1, flags);
208
+}
209
+
210
+static int cmd_update_ref(struct ref_store *refs, const char **argv)
211
+{
212
+ const char *msg = notnull(*argv++, "msg");
213
+ const char *refname = notnull(*argv++, "refname");
214
+ const char *new_sha1_buf = notnull(*argv++, "old-sha1");
215
+ const char *old_sha1_buf = notnull(*argv++, "old-sha1");
216
+ unsigned int flags = arg_flags(*argv++, "flags");
217
+ unsigned char old_sha1[20];
218
+ unsigned char new_sha1[20];
219
+
220
+ if (get_sha1_hex(old_sha1_buf, old_sha1) ||
221
+ get_sha1_hex(new_sha1_buf, new_sha1))
222
+ die("not sha-1");
223
+
224
+ return refs_update_ref(refs, msg, refname,
225
+ new_sha1, old_sha1,
226
+ flags, UPDATE_REFS_DIE_ON_ERR);
227
+}
228
+
229
+struct command {
230
+ const char *name;
231
+ int (*func)(struct ref_store *refs, const char **argv);
232
+};
233
+
234
+static struct command commands[] = {
235
+ { "pack-refs", cmd_pack_refs },
236
+ { "peel-ref", cmd_peel_ref },
237
+ { "create-symref", cmd_create_symref },
238
+ { "delete-refs", cmd_delete_refs },
239
+ { "rename-ref", cmd_rename_ref },
240
+ { "for-each-ref", cmd_for_each_ref },
241
+ { "resolve-ref", cmd_resolve_ref },
242
+ { "verify-ref", cmd_verify_ref },
243
+ { "for-each-reflog", cmd_for_each_reflog },
244
+ { "for-each-reflog-ent", cmd_for_each_reflog_ent },
245
+ { "for-each-reflog-ent-reverse", cmd_for_each_reflog_ent_reverse },
246
+ { "reflog-exists", cmd_reflog_exists },
247
+ { "create-reflog", cmd_create_reflog },
248
+ { "delete-reflog", cmd_delete_reflog },
249
+ { "reflog-expire", cmd_reflog_expire },
250
+ /*
251
+ * backend transaction functions can't be tested separately
252
+ */
253
+ { "delete-ref", cmd_delete_ref },
254
+ { "update-ref", cmd_update_ref },
255
+ { NULL, NULL }
256
+};
257
+
258
+int cmd_main(int argc, const char **argv)
259
+{
260
+ struct ref_store *refs;
261
+ const char *func;
262
+ struct command *cmd;
263
+
264
+ setup_git_directory();
265
+
266
+ argv = get_store(argv + 1, &refs);
267
+
268
+ func = *argv++;
269
+ if (!func)
270
+ die("ref function required");
271
+ for (cmd = commands; cmd->name; cmd++) {
272
+ if (!strcmp(func, cmd->name))
273
+ return cmd->func(refs, argv);
274
+ }
275
+ die("unknown function %s", func);
276
+ return 0;
277
+}