From: Xing Xin <xingxin.xx@xxxxxxxxxxxxx> Currently, server options for Git protocol v2 can only be specified via the command line option "--server-option" or "-o", which is inconvenient when users want to specify a list of default options to send. Therefore, we are introducing a new configuration to hold a list of default server options, akin to the `push.pushOption` configuration for push options. Initially, I named the new configuration `fetch.serverOption` to align with `push.pushOption`. However, after discussing with Patrick, it was renamed to `remote.<name>.serverOption` as suggested, because: 1. Server options are designed to be server-specific, making it more logical to use a per-remote configuration. 2. Using "fetch." prefixed configurations in git-clone or git-ls-remote seems out of place and inconsistent in design. The parsing logic for `remote.<name>.serverOption` also relies on `transport.c:parse_transport_option`, similar to `push.pushOption`, and they follow the same priority design: 1. Server options set in lower-priority configuration files (e.g., /etc/gitconfig or $HOME/.gitconfig) can be overridden or unset in more specific repository configurations using an empty string. 2. Command-line specified server options take precedence over those from the configuration. Server options from configuration are stored to the corresponding `remote.h:remote` as a new field `server_options`. The field will be utilized in the subsequent commit to help initialize the `server_options` of `transport.h:transport`. And documentation have been updated accordingly. Helped-by: Patrick Steinhardt <ps@xxxxxx> Helped-by: Junio C Hamano <gitster@xxxxxxxxx> Reported-by: Liu Zhongbo <liuzhongbo.6666@xxxxxxxxxxxxx> Signed-off-by: Xing Xin <xingxin.xx@xxxxxxxxxxxxx> --- Documentation/config/remote.txt | 10 ++++++++++ remote.c | 7 +++++++ remote.h | 3 +++ 3 files changed, 20 insertions(+) diff --git a/Documentation/config/remote.txt b/Documentation/config/remote.txt index 8efc53e836d..8ba48573fb6 100644 --- a/Documentation/config/remote.txt +++ b/Documentation/config/remote.txt @@ -95,3 +95,13 @@ remote.<name>.partialclonefilter:: Changing or clearing this value will only affect fetches for new commits. To fetch associated objects for commits already present in the local object database, use the `--refetch` option of linkgit:git-fetch[1]. + +remote.<name>.serverOption:: + When no `--server-option=<option>` argument is given from the command + line, git will use the values from this configuration as a default list of + server options for this remote. ++ +This is a multi-valued variable, and an empty value can be used in a higher +priority configuration file (e.g. `.git/config` in a repository) to clear +the values inherited from a lower priority configuration files (e.g. +`$HOME/.gitconfig`). diff --git a/remote.c b/remote.c index 7d5b8f750d8..fe11ead27ad 100644 --- a/remote.c +++ b/remote.c @@ -24,6 +24,7 @@ #include "advice.h" #include "connect.h" #include "parse-options.h" +#include "transport.h" enum map_direction { FROM_SRC, FROM_DST }; @@ -125,6 +126,7 @@ static struct remote *make_remote(struct remote_state *remote_state, struct remote *ret; struct remotes_hash_key lookup; struct hashmap_entry lookup_entry, *e; + struct string_list server_options = STRING_LIST_INIT_DUP; if (!len) len = strlen(name); @@ -143,6 +145,7 @@ static struct remote *make_remote(struct remote_state *remote_state, ret->name = xstrndup(name, len); refspec_init(&ret->push, REFSPEC_PUSH); refspec_init(&ret->fetch, REFSPEC_FETCH); + ret->server_options = server_options; ALLOC_GROW(remote_state->remotes, remote_state->remotes_nr + 1, remote_state->remotes_alloc); @@ -166,6 +169,7 @@ static void remote_clear(struct remote *remote) free((char *)remote->uploadpack); FREE_AND_NULL(remote->http_proxy); FREE_AND_NULL(remote->http_proxy_authmethod); + string_list_clear(&remote->server_options, 0); } static void add_merge(struct branch *branch, const char *name) @@ -482,6 +486,9 @@ static int handle_config(const char *key, const char *value, key, value); } else if (!strcmp(subkey, "vcs")) { return git_config_string(&remote->foreign_vcs, key, value); + } else if (!strcmp(subkey, "serveroption")) { + return parse_transport_option(key, value, + &remote->server_options); } return 0; } diff --git a/remote.h b/remote.h index b901b56746d..d9926a76d23 100644 --- a/remote.h +++ b/remote.h @@ -4,6 +4,7 @@ #include "hash.h" #include "hashmap.h" #include "refspec.h" +#include "string-list.h" #include "strvec.h" struct option; @@ -104,6 +105,8 @@ struct remote { /* The method used for authenticating against `http_proxy`. */ char *http_proxy_authmethod; + + struct string_list server_options; }; /** -- gitgitgadget