summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGlen Choo <chooglen@google.com>2022-10-28 20:14:51 +0000
committerTaylor Blau <me@ttaylorr.com>2022-10-30 14:19:27 -0400
commit09b1f7531afc6399339e836798834fd721b02adc (patch)
treeb4025314e3c54720739973a8091cc14d6b2792e0
parent9082f18392c010bfb8f690b9165ac0a2eb03ac00 (diff)
downloadgit-09b1f7531afc6399339e836798834fd721b02adc.tar.gz
submodule--helper clone: create named branch
When submodule branching is enabled (i.e. "submodule.propagateBranches = true"), submodules are expected to have the same set of branches as the superproject. To support this behavior in newly cloned submodules, teach "git submodule--helper clone" to: - clone with the "--detach" flag (so that the submodule doesn't create a branch corresponding to the remote's HEAD) - create a branch when using the --branch and --branch-oid flags The --branch and --branch-oid flags are only allowed when submodule branching is enabled, otherwise the named branch might conflict with the branch from the submodule remote's HEAD. This functionality will be tested in a later commit where "git submodule update" uses it to create and check out the correct branch when submodule branching is enabled. "git submodule add" (which also invokes "git submodule--helper clone") should also do something similar when submodule branching is enabled, but this is left for a later series. Arguably, "--detach" should also be the default for "submodule.propagateBranches=false" since it doesn't make sense to create a submodule branch when the submodule is always expected to be in detached HEAD. But, to be conservative, this commit does not change the behavior of "submodule.propagateBranches=false". Signed-off-by: Glen Choo <chooglen@google.com> Signed-off-by: Taylor Blau <me@ttaylorr.com>
-rw-r--r--builtin/submodule--helper.c33
1 files changed, 33 insertions, 0 deletions
diff --git a/builtin/submodule--helper.c b/builtin/submodule--helper.c
index 0b4acb442b..c974206cad 100644
--- a/builtin/submodule--helper.c
+++ b/builtin/submodule--helper.c
@@ -1503,6 +1503,8 @@ struct module_clone_data {
const char *name;
const char *url;
const char *depth;
+ const char *branch;
+ const char *branch_oid;
struct list_objects_filter_options *filter_options;
unsigned int quiet: 1;
unsigned int progress: 1;
@@ -1692,6 +1694,8 @@ static int clone_submodule(const struct module_clone_data *clone_data,
strvec_push(&cp.args, clone_data->single_branch ?
"--single-branch" :
"--no-single-branch");
+ if (the_repository->settings.submodule_propagate_branches)
+ strvec_push(&cp.args, "--detach");
strvec_push(&cp.args, "--");
strvec_push(&cp.args, clone_data->url);
@@ -1704,6 +1708,21 @@ static int clone_submodule(const struct module_clone_data *clone_data,
if(run_command(&cp))
die(_("clone of '%s' into submodule path '%s' failed"),
clone_data->url, clone_data_path);
+
+ if (clone_data->branch) {
+ struct child_process branch_cp = CHILD_PROCESS_INIT;
+
+ branch_cp.git_cmd = 1;
+ prepare_other_repo_env(&branch_cp.env, sm_gitdir);
+
+ strvec_pushl(&branch_cp.args, "branch",
+ clone_data->branch, clone_data->branch_oid,
+ NULL);
+
+ if (run_command(&branch_cp))
+ die(_("could not create branch '%s' in submodule path '%s'"),
+ clone_data->branch, clone_data_path);
+ }
} else {
char *path;
@@ -1778,6 +1797,12 @@ static int module_clone(int argc, const char **argv, const char *prefix)
N_("disallow cloning into non-empty directory")),
OPT_BOOL(0, "single-branch", &clone_data.single_branch,
N_("clone only one branch, HEAD or --branch")),
+ OPT_STRING(0, "branch", &clone_data.branch,
+ N_("string"),
+ N_("name of branch to be created")),
+ OPT_STRING(0, "branch-oid", &clone_data.branch_oid,
+ N_("object-id"),
+ N_("commit id for new branch")),
OPT_PARSE_LIST_OBJECTS_FILTER(&filter_options),
OPT_END()
};
@@ -1785,12 +1810,14 @@ static int module_clone(int argc, const char **argv, const char *prefix)
N_("git submodule--helper clone [--prefix=<path>] [--quiet] "
"[--reference <repository>] [--name <name>] [--depth <depth>] "
"[--single-branch] [--filter <filter-spec>] "
+ "[--branch <branch> --branch-oid <oid>]"
"--url <url> --path <path>"),
NULL
};
argc = parse_options(argc, argv, prefix, module_clone_options,
git_submodule_helper_usage, 0);
+ prepare_repo_settings(the_repository);
clone_data.dissociate = !!dissociate;
clone_data.quiet = !!quiet;
@@ -1802,6 +1829,12 @@ static int module_clone(int argc, const char **argv, const char *prefix)
usage_with_options(git_submodule_helper_usage,
module_clone_options);
+ if (!!clone_data.branch != !!clone_data.branch_oid)
+ BUG("--branch and --branch-oid must be set/unset together");
+ if ((clone_data.branch &&
+ !the_repository->settings.submodule_propagate_branches))
+ BUG("--branch is only expected with submodule.propagateBranches");
+
clone_submodule(&clone_data, &reference);
list_objects_filter_release(&filter_options);
string_list_clear(&reference, 1);