On repository with multiple submodules, one may need to run a command based on submodule trait. This changes add flags to submodule--helper foreachto fulfill this need by: Adding the flag --[no-]active to filter submodule based on the active state. Adding the flag --[no-]populated to filter submodule based on the fact that it is populated or not. Adding the flag -b|--branch <branch> to filter submodule based on the tracking branch. Signed-off-by: Guillaume Galeazzi guillaume.galeazzi@xxxxxxxxx [guillaume.galeazzi@xxxxxxxxx] Guillaume Galeazzi (3): submodule--helper.c: add active to foreach submodule--helper.c: add populated to foreach submodule--helper.c: add branch to foreach builtin/submodule--helper.c | 60 ++++++++++++++++++++++++++++++------ t/t7407-submodule-foreach.sh | 60 ++++++++++++++++++++++++++++++++++++ 2 files changed, 110 insertions(+), 10 deletions(-) base-commit: b994622632154fc3b17fb40a38819ad954a5fb88 Published-As: https://github.com/gitgitgadget/git/releases/tag/pr-631%2Fgzzi%2Fsubmodule-only-active-v2 Fetch-It-Via: git fetch https://github.com/gitgitgadget/git pr-631/gzzi/submodule-only-active-v2 Pull-Request: https://github.com/gitgitgadget/git/pull/631 Range-diff vs v1: 1: 77bb291af5d ! 1: 90defeb5a75 submodule--helper.c: add only-active to foreach @@ Metadata Author: Guillaume Galeazzi <guillaume.galeazzi@xxxxxxxxx> ## Commit message ## - submodule--helper.c: add only-active to foreach - - On repository with some submodule not active, it could be needed to run - a command only for active submodule. Today it can be achived with the - command: + submodule--helper.c: add active to foreach + On a repository with some submodules not active, one may need to run a + command only for an active submodule or vice-versa. To achieve this, + one may use: git submodule foreach 'git -C $toplevel submodule--helper is-active \ $sm_path && pwd || :' - Goal of this change is to make it more accessible by adding the flag - --only-active to the submodule--helper command. Previous example - become: - - git submodule--helper foreach --only-active pwd + Simplify this expression to make it more readable and easy-to-use by + adding the flat `--[no-]active` to subcommand `foreach` of `git + submodule`. Thus, simplifying the above command to: + git submodule--helper foreach --active pwd Signed-off-by: Guillaume Galeazzi <guillaume.galeazzi@xxxxxxxxx> @@ builtin/submodule--helper.c: struct foreach_cb { const char *prefix; int quiet; int recursive; -+ int only_active; ++ int active_only; }; - #define FOREACH_CB_INIT { 0 } +-#define FOREACH_CB_INIT { 0 } + +-static void runcommand_in_submodule_cb(const struct cache_entry *list_item, +- void *cb_data) ++#define FOREACH_BOOL_FILTER_NOT_SET -1 ++ ++#define FOREACH_CB_INIT { .active_only=FOREACH_BOOL_FILTER_NOT_SET } ++ ++static void runcommand_in_submodule(const struct cache_entry *list_item, ++ struct foreach_cb *info) + { +- struct foreach_cb *info = cb_data; + const char *path = list_item->name; + const struct object_id *ce_oid = &list_item->oid; @@ builtin/submodule--helper.c: static void runcommand_in_submodule_cb(const struct cache_entry *list_item, - struct child_process cp = CHILD_PROCESS_INIT; - char *displaypath; + free(displaypath); + } -+ if (info->only_active && !is_submodule_active(the_repository, path)) -+ return; ++static void runcommand_in_submodule_filtered_cb(const struct cache_entry *list_item, ++ void *cb_data) ++{ ++ const char *path = list_item->name; ++ struct foreach_cb *info = cb_data; ++ int is_active; + - displaypath = get_submodule_displaypath(path, info->prefix); - - sub = submodule_from_path(the_repository, &null_oid, path); ++ if (info->active_only != FOREACH_BOOL_FILTER_NOT_SET) { ++ is_active = is_submodule_active(the_repository, path); ++ if (is_active != info->active_only) ++ return; ++ } ++ ++ runcommand_in_submodule(list_item, info); ++} ++ + static int module_foreach(int argc, const char **argv, const char *prefix) + { + struct foreach_cb info = FOREACH_CB_INIT; @@ builtin/submodule--helper.c: static int module_foreach(int argc, const char **argv, const char *prefix) OPT__QUIET(&info.quiet, N_("Suppress output of entering each submodule command")), OPT_BOOL(0, "recursive", &info.recursive, N_("Recurse into nested submodules")), -+ OPT_BOOL(0, "only-active", &info.only_active, -+ N_("Call command only for active submodules")), ++ OPT_BOOL(0, "active", &info.active_only, ++ N_("Call command depending on submodule active state")), OPT_END() }; const char *const git_submodule_helper_usage[] = { - N_("git submodule--helper foreach [--quiet] [--recursive] [--] <command>"), -+ N_("git submodule--helper foreach [--quiet] [--recursive] [--only-active] [--] <command>"), ++ N_("git submodule--helper foreach [--quiet] [--recursive] [--[no-]active] [--] <command>"), NULL }; +@@ builtin/submodule--helper.c: static int module_foreach(int argc, const char **argv, const char *prefix) + info.argv = argv; + info.prefix = prefix; + +- for_each_listed_submodule(&list, runcommand_in_submodule_cb, &info); ++ for_each_listed_submodule(&list, runcommand_in_submodule_filtered_cb, &info); + + return 0; + } ## t/t7407-submodule-foreach.sh ## @@ t/t7407-submodule-foreach.sh: test_expect_success 'test basic "submodule foreach" usage' ' test_i18ncmp expect actual ' -+sub3sha1=$(cd super/sub3 && git rev-parse HEAD) +cat > expect <<EOF +Entering 'sub3' +$pwd/clone-foo3-sub3-$sub3sha1 +EOF + -+test_expect_success 'test "submodule--helper foreach --only-active" usage' ' ++test_expect_success 'test "submodule--helper foreach --active" usage' ' ++ test_when_finished "git -C clone config --unset submodule.foo1.active" && ++ ( ++ cd clone && ++ git config --bool submodule.foo1.active "false" && ++ git submodule--helper foreach --active "echo \$toplevel-\$name-\$path-\$sha1" > ../actual ++ ) && ++ test_i18ncmp expect actual ++' ++ ++cat > expect <<EOF ++Entering 'sub1' ++$pwd/clone-foo1-sub1-$sub1sha1 ++EOF ++ ++test_expect_success 'test "submodule--helper foreach --no-active" usage' ' + test_when_finished "git -C clone config --unset submodule.foo1.active" && + ( + cd clone && + git config --bool submodule.foo1.active "false" && -+ git submodule--helper foreach --only-active "echo \$toplevel-\$name-\$path-\$sha1" > ../actual ++ git submodule--helper foreach --no-active "echo \$toplevel-\$name-\$path-\$sha1" > ../actual + ) && + test_i18ncmp expect actual +' -: ----------- > 2: f9cbdcdeacf submodule--helper.c: add populated to foreach -: ----------- > 3: 65504cb780a submodule--helper.c: add branch to foreach -- gitgitgadget