Skip to content

Commit 3d8e3dc

Browse files
committed
Merge branch 'ds/rebase-update-ref'
"git rebase -i" learns to update branches whose tip appear in the rebased range with "--update-refs" option. source: <[email protected]> * ds/rebase-update-ref: sequencer: notify user of --update-refs activity sequencer: ignore HEAD ref under --update-refs rebase: add rebase.updateRefs config option sequencer: rewrite update-refs as user edits todo list rebase: update refs from 'update-ref' commands rebase: add --update-refs option sequencer: add update-ref command sequencer: define array with enum values rebase-interactive: update 'merge' description branch: consider refs under 'update-refs' t2407: test branches currently using apply backend t2407: test bisect and rebase as black-boxes
2 parents e59acea + 4611884 commit 3d8e3dc

File tree

10 files changed

+895
-44
lines changed

10 files changed

+895
-44
lines changed

Documentation/config/rebase.txt

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,9 @@ rebase.autoStash::
2121
`--autostash` options of linkgit:git-rebase[1].
2222
Defaults to false.
2323

24+
rebase.updateRefs::
25+
If set to true enable `--update-refs` option by default.
26+
2427
rebase.missingCommitsCheck::
2528
If set to "warn", git rebase -i will print a warning if some
2629
commits are removed (e.g. a line was deleted), however the

Documentation/git-rebase.txt

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -612,6 +612,15 @@ provided. Otherwise an explicit `--no-reschedule-failed-exec` at the
612612
start would be overridden by the presence of
613613
`rebase.rescheduleFailedExec=true` configuration.
614614

615+
--update-refs::
616+
--no-update-refs::
617+
Automatically force-update any branches that point to commits that
618+
are being rebased. Any branches that are checked out in a worktree
619+
are not updated in this way.
620+
+
621+
If the configuration variable `rebase.updateRefs` is set, then this option
622+
can be used to override and disable this setting.
623+
615624
INCOMPATIBLE OPTIONS
616625
--------------------
617626

@@ -635,6 +644,7 @@ are incompatible with the following options:
635644
* --empty=
636645
* --reapply-cherry-picks
637646
* --edit-todo
647+
* --update-refs
638648
* --root when used in combination with --onto
639649

640650
In addition, the following pairs of options are incompatible:

branch.c

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -388,6 +388,7 @@ static void prepare_checked_out_branches(void)
388388
char *old;
389389
struct wt_status_state state = { 0 };
390390
struct worktree *wt = worktrees[i++];
391+
struct string_list update_refs = STRING_LIST_INIT_DUP;
391392

392393
if (wt->is_bare)
393394
continue;
@@ -423,6 +424,18 @@ static void prepare_checked_out_branches(void)
423424
strbuf_release(&ref);
424425
}
425426
wt_status_state_free_buffers(&state);
427+
428+
if (!sequencer_get_update_refs_state(get_worktree_git_dir(wt),
429+
&update_refs)) {
430+
struct string_list_item *item;
431+
for_each_string_list_item(item, &update_refs) {
432+
old = strmap_put(&current_checked_out_branches,
433+
item->string,
434+
xstrdup(wt->path));
435+
free(old);
436+
}
437+
string_list_clear(&update_refs, 1);
438+
}
426439
}
427440

428441
free_worktrees(worktrees);

builtin/rebase.c

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,7 @@ struct rebase_options {
102102
int reschedule_failed_exec;
103103
int reapply_cherry_picks;
104104
int fork_point;
105+
int update_refs;
105106
};
106107

107108
#define REBASE_OPTIONS_INIT { \
@@ -298,6 +299,7 @@ static int do_interactive_rebase(struct rebase_options *opts, unsigned flags)
298299
ret = complete_action(the_repository, &replay, flags,
299300
shortrevisions, opts->onto_name, opts->onto,
300301
&opts->orig_head, &commands, opts->autosquash,
302+
opts->update_refs,
301303
&todo_list);
302304
}
303305

@@ -800,6 +802,11 @@ static int rebase_config(const char *var, const char *value, void *data)
800802
return 0;
801803
}
802804

805+
if (!strcmp(var, "rebase.updaterefs")) {
806+
opts->update_refs = git_config_bool(var, value);
807+
return 0;
808+
}
809+
803810
if (!strcmp(var, "rebase.reschedulefailedexec")) {
804811
opts->reschedule_failed_exec = git_config_bool(var, value);
805812
return 0;
@@ -1124,6 +1131,9 @@ int cmd_rebase(int argc, const char **argv, const char *prefix)
11241131
OPT_BOOL(0, "autosquash", &options.autosquash,
11251132
N_("move commits that begin with "
11261133
"squash!/fixup! under -i")),
1134+
OPT_BOOL(0, "update-refs", &options.update_refs,
1135+
N_("update branches that point to commits "
1136+
"that are being rebased")),
11271137
{ OPTION_STRING, 'S', "gpg-sign", &gpg_sign, N_("key-id"),
11281138
N_("GPG-sign commits"),
11291139
PARSE_OPT_OPTARG, NULL, (intptr_t) "" },

rebase-interactive.c

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -54,9 +54,12 @@ void append_todo_help(int command_count,
5454
"l, label <label> = label current HEAD with a name\n"
5555
"t, reset <label> = reset HEAD to a label\n"
5656
"m, merge [-C <commit> | -c <commit>] <label> [# <oneline>]\n"
57-
". create a merge commit using the original merge commit's\n"
58-
". message (or the oneline, if no original merge commit was\n"
59-
". specified); use -c <commit> to reword the commit message\n"
57+
" create a merge commit using the original merge commit's\n"
58+
" message (or the oneline, if no original merge commit was\n"
59+
" specified); use -c <commit> to reword the commit message\n"
60+
"u, update-ref <ref> = track a placeholder for the <ref> to be updated\n"
61+
" to this position in the new commits. The <ref> is\n"
62+
" updated at the end of the rebase\n"
6063
"\n"
6164
"These lines can be re-ordered; they are executed from top to bottom.\n");
6265
unsigned edit_todo = !(shortrevisions && shortonto);
@@ -143,6 +146,12 @@ int edit_todo_list(struct repository *r, struct todo_list *todo_list,
143146
return -4;
144147
}
145148

149+
/*
150+
* See if branches need to be added or removed from the update-refs
151+
* file based on the new todo list.
152+
*/
153+
todo_list_filter_update_refs(r, new_todo);
154+
146155
return 0;
147156
}
148157

0 commit comments

Comments
 (0)