From: Brandon Williams <bmwill@google.com>
To: git@vger.kernel.org, bmwill@google.com
Cc: Brandon Williams <bmwill@google.com>
Subject: [PATCH 2/3] ls-remote: send server options when using protocol v2
Date: Mon, 23 Apr 2018 15:46:23 -0700 [thread overview]
Message-ID: <20180423224624.213341-3-bmwill@google.com> (raw)
In-Reply-To: <20180423224624.213341-1-bmwill@google.com>
Teach ls-remote to optionally accept server options by specifying them
on the cmdline via '-o' or '--server-option'. These server options are
sent to the remote end when querying for the remote end's refs using
protocol version 2.
If communicating using a protocol other than v2 the provided options are
ignored and not sent to the remote end.
Signed-off-by: Brandon Williams <bmwill@google.com>
---
Documentation/git-ls-remote.txt | 8 ++++++++
builtin/ls-remote.c | 4 ++++
connect.c | 9 ++++++++-
remote.h | 4 +++-
t/t5702-protocol-v2.sh | 16 ++++++++++++++++
transport.c | 2 +-
transport.h | 6 ++++++
7 files changed, 46 insertions(+), 3 deletions(-)
diff --git a/Documentation/git-ls-remote.txt b/Documentation/git-ls-remote.txt
index 5f2628c8f..e5defb1b2 100644
--- a/Documentation/git-ls-remote.txt
+++ b/Documentation/git-ls-remote.txt
@@ -60,6 +60,14 @@ OPTIONS
upload-pack only shows the symref HEAD, so it will be the only
one shown by ls-remote.
+-o <option>::
+--server-option=<option>::
+ Transmit the given string to the server when communicating using
+ protocol version 2. The given string must not contain a NUL or LF
+ character.
+ When multiple `--server-option=<option>` are given, they are all
+ sent to the other side in the order listed on the command line.
+
<repository>::
The "remote" repository to query. This parameter can be
either a URL or the name of a remote (see the GIT URLS and
diff --git a/builtin/ls-remote.c b/builtin/ls-remote.c
index 380c18027..3150bfb92 100644
--- a/builtin/ls-remote.c
+++ b/builtin/ls-remote.c
@@ -45,6 +45,7 @@ int cmd_ls_remote(int argc, const char **argv, const char *prefix)
const char *uploadpack = NULL;
const char **pattern = NULL;
struct argv_array ref_prefixes = ARGV_ARRAY_INIT;
+ struct string_list server_options = STRING_LIST_INIT_DUP;
struct remote *remote;
struct transport *transport;
@@ -67,6 +68,7 @@ int cmd_ls_remote(int argc, const char **argv, const char *prefix)
2, PARSE_OPT_NOCOMPLETE),
OPT_BOOL(0, "symref", &show_symref_target,
N_("show underlying ref in addition to the object pointed by it")),
+ OPT_STRING_LIST('o', "server-option", &server_options, N_("server-specific"), N_("option to transmit")),
OPT_END()
};
@@ -107,6 +109,8 @@ int cmd_ls_remote(int argc, const char **argv, const char *prefix)
transport = transport_get(remote, NULL);
if (uploadpack != NULL)
transport_set_option(transport, TRANS_OPT_UPLOADPACK, uploadpack);
+ if (server_options.nr)
+ transport->server_options = &server_options;
ref = transport_get_remote_refs(transport, &ref_prefixes);
if (transport_disconnect(transport))
diff --git a/connect.c b/connect.c
index 54971166a..3000768c7 100644
--- a/connect.c
+++ b/connect.c
@@ -408,7 +408,8 @@ static int process_ref_v2(const char *line, struct ref ***list)
struct ref **get_remote_refs(int fd_out, struct packet_reader *reader,
struct ref **list, int for_push,
- const struct argv_array *ref_prefixes)
+ const struct argv_array *ref_prefixes,
+ const struct string_list *server_options)
{
int i;
*list = NULL;
@@ -419,6 +420,12 @@ struct ref **get_remote_refs(int fd_out, struct packet_reader *reader,
if (server_supports_v2("agent", 0))
packet_write_fmt(fd_out, "agent=%s", git_user_agent_sanitized());
+ if (server_options && server_options->nr &&
+ server_supports_v2("server-option", 1))
+ for (i = 0; i < server_options->nr; i++)
+ packet_write_fmt(fd_out, "server-option=%s",
+ server_options->items[i].string);
+
packet_delim(fd_out);
/* When pushing we don't want to request the peeled tags */
if (!for_push)
diff --git a/remote.h b/remote.h
index 2b3180f94..93dd97e25 100644
--- a/remote.h
+++ b/remote.h
@@ -153,6 +153,7 @@ void free_refs(struct ref *ref);
struct oid_array;
struct packet_reader;
struct argv_array;
+struct string_list;
extern struct ref **get_remote_heads(struct packet_reader *reader,
struct ref **list, unsigned int flags,
struct oid_array *extra_have,
@@ -161,7 +162,8 @@ extern struct ref **get_remote_heads(struct packet_reader *reader,
/* Used for protocol v2 in order to retrieve refs from a remote */
extern struct ref **get_remote_refs(int fd_out, struct packet_reader *reader,
struct ref **list, int for_push,
- const struct argv_array *ref_prefixes);
+ const struct argv_array *ref_prefixes,
+ const struct string_list *server_options);
int resolve_remote_symref(struct ref *ref, struct ref *list);
int ref_newer(const struct object_id *new_oid, const struct object_id *old_oid);
diff --git a/t/t5702-protocol-v2.sh b/t/t5702-protocol-v2.sh
index 56f7c3c32..71ef1aee1 100755
--- a/t/t5702-protocol-v2.sh
+++ b/t/t5702-protocol-v2.sh
@@ -154,6 +154,22 @@ test_expect_success 'ref advertisment is filtered with ls-remote using protocol
test_cmp actual expect
'
+test_expect_success 'server-options are sent when using ls-remote' '
+ test_when_finished "rm -f log" &&
+
+ GIT_TRACE_PACKET="$(pwd)/log" git -c protocol.version=2 \
+ ls-remote -o hello -o world "file://$(pwd)/file_parent" master >actual &&
+
+ cat >expect <<-EOF &&
+ $(git -C file_parent rev-parse refs/heads/master)$(printf "\t")refs/heads/master
+ EOF
+
+ test_cmp actual expect &&
+ grep "server-option=hello" log &&
+ grep "server-option=world" log
+'
+
+
test_expect_success 'clone with file:// using protocol v2' '
test_when_finished "rm -f log" &&
diff --git a/transport.c b/transport.c
index 4d8beaaab..42fd468f3 100644
--- a/transport.c
+++ b/transport.c
@@ -218,7 +218,7 @@ static struct ref *get_refs_via_connect(struct transport *transport, int for_pus
switch (data->version) {
case protocol_v2:
get_remote_refs(data->fd[1], &reader, &refs, for_push,
- ref_prefixes);
+ ref_prefixes, transport->server_options);
break;
case protocol_v1:
case protocol_v0:
diff --git a/transport.h b/transport.h
index e783cfa07..73a7be3c8 100644
--- a/transport.h
+++ b/transport.h
@@ -71,6 +71,12 @@ struct transport {
*/
const struct string_list *push_options;
+ /*
+ * These strings will be passed to the remote side on each command
+ * request, if both sides support the server-option capability.
+ */
+ const struct string_list *server_options;
+
char *pack_lockfile;
signed verbose : 3;
/**
--
2.17.0.484.g0c8726318c-goog
next prev parent reply other threads:[~2018-04-23 22:46 UTC|newest]
Thread overview: 5+ messages / expand[flat|nested] mbox.gz Atom feed top
2018-04-23 22:46 [PATCH 0/3] optionally send server-options when using v2 Brandon Williams
2018-04-23 22:46 ` [PATCH 1/3] serve: introduce the server-option capability Brandon Williams
2018-04-23 22:46 ` Brandon Williams [this message]
2018-04-23 22:46 ` [PATCH 3/3] fetch: send server options when using protocol v2 Brandon Williams
2018-04-23 22:47 ` [PATCH 0/3] optionally send server-options when using v2 Brandon Williams
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20180423224624.213341-3-bmwill@google.com \
--to=bmwill@google.com \
--cc=git@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.