is it possible to go from this:
a--b--c--f
\
d--e
to this?
a--b--c--d--e--f
I'm a bit lost on this one. Any help will be welcome.
is it possible to go from this:
a--b--c--f
\
d--e
to this?
a--b--c--d--e--f
I'm a bit lost on this one. Any help will be welcome.
Not exactly. Git cannot move commits, it can only copy and create new, different commits. To achieve want you want do
git checkout e
git cherry-pick f
You will have
a--b--c--d--e--f`
where f` is a copy of f.
The piece missing from your diagram is the branch names that point to commits f
and e
:
a--b--c--f <-- branch_f
\
d--e <-- branch_e
You cannot literally move commit f
: a commit, once made, is quite permanent and unchange-able. You can, however, copy commit f
to a new commit that's a lot like f
, but different in some way(s).
What you want is a commit that is like f
, except that it has e
as its parent, and probably has a different source base (e
's source rather than c
's).
To get this kind of copy, one can use git cherry-pick
, which literally just makes the copy:
$ git checkout branch_e
$ git cherry-pick branch_f
giving:
a--b--c--f <-- branch_f
\
d--e--f' <-- branch_e (HEAD)
Note that we've added the new commit f'
(the copy) to the current branch, branch_e
.
Instead of using git cherry-pick
, we can use git rebase
. This copies some number of commits, automatically:
$ git checkout branch_f
$ git rebase branch_e
The set of commits that get copied are those on the current branch—which is why we have to check out branch_f
first—that aren't on the other branch, which is why we tell it branch_e
.
The place it copies them to, is "after the tip of the other branch".
Once it finishes making the copy, git rebase
"peels away" the label branch_f
from where it was before, and moves it to after the last-copied commit:
a--b--c--f [abandoned]
\
d--e <-- branch_e
\
f' <-- branch_f (HEAD)
Note that this is the same set of commits as before: the key difference is that branch_e
has not moved (still points to e
) and branch_f
has moved (now points to new copy f'
).
(Also, the current branch is branch_f
this time.)