Skip to content

Commit ffc1873

Browse files
committed
scalar: add the cache-server command
This allows setting the GVFS-enabled cache server, or listing the one(s) associated with the remote repository. Signed-off-by: Johannes Schindelin <johannes.schindelin@gmx.de>
1 parent 9371c15 commit ffc1873

File tree

3 files changed

+150
-1
lines changed

3 files changed

+150
-1
lines changed

Documentation/scalar.adoc

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ scalar run ( all | config | commit-graph | fetch | loose-objects | pack-files )
1919
scalar reconfigure [--maintenance=(enable|disable|keep)] [ --all | <enlistment> ]
2020
scalar diagnose [<enlistment>]
2121
scalar delete <enlistment>
22+
scalar cache-server ( --get | --set <url> | --list [<remote>] ) [<enlistment>]
2223

2324
DESCRIPTION
2425
-----------
@@ -210,6 +211,27 @@ delete <enlistment>::
210211
This subcommand lets you delete an existing Scalar enlistment from your
211212
local file system, unregistering the repository.
212213

214+
Cache-server
215+
~~~~~~~~~~~~
216+
217+
cache-server ( --get | --set <url> | --list [<remote>] ) [<enlistment>]::
218+
This command lets you query or set the GVFS-enabled cache server used
219+
to fetch missing objects.
220+
221+
--get::
222+
This is the default command mode: query the currently-configured cache
223+
server URL, if any.
224+
225+
--list::
226+
Access the `gvfs/info` endpoint of the specified remote (default:
227+
`origin`) to figure out which cache servers are available, if any.
228+
+
229+
In contrast to the `--get` command mode (which only accesses the local
230+
repository), this command mode triggers a request via the network that
231+
potentially requires authentication. If authentication is required, the
232+
configured credential helper is employed (see linkgit:git-credential[1]
233+
for details).
234+
213235
SEE ALSO
214236
--------
215237
linkgit:git-clone[1], linkgit:git-maintenance[1].

scalar.c

Lines changed: 94 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@
2424
#include "wrapper.h"
2525
#include "trace2.h"
2626
#include "json-parser.h"
27+
#include "remote.h"
2728
#include "path.h"
2829

2930
static int is_unattended(void) {
@@ -378,6 +379,21 @@ static int set_config(const char *fmt, ...)
378379
return res;
379380
}
380381

382+
static int list_cache_server_urls(struct json_iterator *it)
383+
{
384+
const char *p;
385+
char *q;
386+
long l;
387+
388+
if (it->type == JSON_STRING &&
389+
skip_iprefix(it->key.buf, ".CacheServers[", &p) &&
390+
(l = strtol(p, &q, 10)) >= 0 && p != q &&
391+
!strcasecmp(q, "].Url"))
392+
printf("#%ld: %s\n", l, it->string_value.buf);
393+
394+
return 0;
395+
}
396+
381397
/* Find N for which .CacheServers[N].GlobalDefault == true */
382398
static int get_cache_server_index(struct json_iterator *it)
383399
{
@@ -448,6 +464,18 @@ static int supports_gvfs_protocol(const char *url, char **cache_server_url)
448464
JSON_ITERATOR_INIT(out.buf, get_cache_server_index, &l);
449465
struct cache_server_url_data data = { .url = NULL };
450466

467+
if (!cache_server_url) {
468+
it.fn = list_cache_server_urls;
469+
if (iterate_json(&it) < 0) {
470+
reset_iterator(&it);
471+
strbuf_release(&out);
472+
return error("JSON parse error");
473+
}
474+
reset_iterator(&it);
475+
strbuf_release(&out);
476+
return 0;
477+
}
478+
451479
if (iterate_json(&it) < 0) {
452480
reset_iterator(&it);
453481
strbuf_release(&out);
@@ -468,7 +496,9 @@ static int supports_gvfs_protocol(const char *url, char **cache_server_url)
468496
return 1;
469497
}
470498
strbuf_release(&out);
471-
return 0; /* error out quietly */
499+
/* error out quietly, unless we wanted to list URLs */
500+
return cache_server_url ?
501+
0 : error(_("Could not access gvfs/config endpoint"));
472502
}
473503

474504
static char *default_cache_root(const char *root)
@@ -1345,6 +1375,68 @@ static int cmd_version(int argc, const char **argv)
13451375
return 0;
13461376
}
13471377

1378+
static int cmd_cache_server(int argc, const char **argv)
1379+
{
1380+
int get = 0;
1381+
const char *set = NULL, *list = NULL;
1382+
struct option options[] = {
1383+
OPT_CMDMODE(0, "get", &get,
1384+
N_("get the configured cache-server URL"), 1),
1385+
OPT_STRING(0, "set", &set, N_("URL"),
1386+
N_("configure the cache-server to use")),
1387+
OPT_STRING(0, "list", &list, N_("remote"),
1388+
N_("list the possible cache-server URLs")),
1389+
OPT_END(),
1390+
};
1391+
const char * const usage[] = {
1392+
N_("scalar cache-server "
1393+
"[--get | --set <url> | --list <remote>] [<enlistment>]"),
1394+
NULL
1395+
};
1396+
int res = 0;
1397+
1398+
argc = parse_options(argc, argv, NULL, options,
1399+
usage, 0);
1400+
1401+
if (get + !!set + !!list > 1)
1402+
usage_msg_opt(_("--get/--set/--list are mutually exclusive"),
1403+
usage, options);
1404+
1405+
setup_enlistment_directory(argc, argv, usage, options, NULL);
1406+
1407+
if (list) {
1408+
const char *name = list, *url = list;
1409+
1410+
if (!strchr(list, '/')) {
1411+
struct remote *remote;
1412+
1413+
/* Look up remote */
1414+
remote = remote_get(list);
1415+
if (!remote) {
1416+
error("no such remote: '%s'", name);
1417+
return 1;
1418+
}
1419+
if (!remote->url.nr) {
1420+
return error(_("remote '%s' has no URLs"),
1421+
name);
1422+
}
1423+
url = remote->url.v[0];
1424+
}
1425+
res = supports_gvfs_protocol(url, NULL);
1426+
} else if (set) {
1427+
res = set_config("gvfs.cache-server=%s", set);
1428+
} else {
1429+
char *url = NULL;
1430+
1431+
printf("Using cache server: %s\n",
1432+
repo_config_get_string(the_repository, "gvfs.cache-server", &url) ?
1433+
"(undefined)" : url);
1434+
free(url);
1435+
}
1436+
1437+
return !!res;
1438+
}
1439+
13481440
static struct {
13491441
const char *name;
13501442
int (*fn)(int, const char **);
@@ -1359,6 +1451,7 @@ static struct {
13591451
{ "help", cmd_help },
13601452
{ "version", cmd_version },
13611453
{ "diagnose", cmd_diagnose },
1454+
{ "cache-server", cmd_cache_server },
13621455
{ NULL, NULL},
13631456
};
13641457

t/t9210-scalar.sh

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -484,4 +484,38 @@ test_expect_success '`scalar delete` with existing repo' '
484484
test_path_is_missing existing
485485
'
486486

487+
test_expect_success 'scalar cache-server basics' '
488+
repo=with-cache-server &&
489+
git init $repo &&
490+
scalar cache-server --get $repo >out &&
491+
cat >expect <<-EOF &&
492+
Using cache server: (undefined)
493+
EOF
494+
test_cmp expect out &&
495+
496+
scalar cache-server --set http://fake-server/url $repo &&
497+
test_cmp_config -C $repo http://fake-server/url gvfs.cache-server &&
498+
scalar delete $repo &&
499+
test_path_is_missing $repo
500+
'
501+
502+
test_expect_success 'scalar cache-server list URL' '
503+
repo=with-real-gvfs &&
504+
git init $repo &&
505+
git -C $repo remote add origin http://$HOST_PORT/ &&
506+
scalar cache-server --list origin $repo >out &&
507+
508+
cat >expect <<-EOF &&
509+
#0: http://$HOST_PORT/servertype/cache
510+
EOF
511+
512+
test_cmp expect out &&
513+
514+
test_must_fail scalar -C $repo cache-server --list 2>err &&
515+
grep "requires a value" err &&
516+
517+
scalar delete $repo &&
518+
test_path_is_missing $repo
519+
'
520+
487521
test_done

0 commit comments

Comments
 (0)