Reputation: 5542
I'm new to GIT and I can't figure out if my question already has an answer. Please read it carefully before marking it as duplicate.
I have a branch, let's call it public
, which is pushed and in sync with origin
. At one point, I create another branch, private
, which pops out of public
, because I want to do a lot of work which I want to remain secret. So I only work on private
and I do, let's say, 10 commits, until I finally arrive to a state which can be made public.
Now, I obviously don't want to do a fast-forward merge of public
because all the intermediary commits would appear on the remote server.
How can I do a rebase
given that the public
branch has not diverged from the point where private
was created.
Clearly, I want to create a new commit on the public
branch that contains all the modifications from the 10 private
commits. I know that translates into a rebase
, but I don't know how to do it.
Upvotes: 4
Views: 2005
Reputation: 41945
To be exact, creating a new commit on public
that contains the modifications from private
does not call for rebase
. It calls for merge
.
Rebasing to squash together the commits of private
before seems to be what you want, you keep a branch and a merge commit.
However since you don't care about the detailed history of your private
branch, you could just as well:
$ git checkout public
$ git merge --squash private
$ git commit
The index is first updated with the content of private
, and you can make a single commit of it on top of public
.
Upvotes: 3
Reputation: 75545
First of all, the fact that public
is tracking a remote branch that lives on origin
does not mean that the local branch public
is equivalent to the remote branch origin/public
.
Because of git's distributed nature, you can make a bunch of commits on your local public
branch without anything making it to the server, as long as you do not push.
With respect to what you are trying to do given the current state of your system, here are some detailed steps, assuming you do not care about keeping your original 10 commits.
Begin interactive rebase against the current state of the remote server.
git checkout private
git rebase -i origin/public
An editor will pop up. The specific editor will depend on the platform and the environmental variable settings. Inside this editor, you will see the hashes of your 10 commits, with the word "pick" in the left hand column. For the first row, keep pick
. For the subsequent rows, replace pick
with squash
. Save the file and quit the editor.
At this point, git
will have merged the 10 commits into a single commit, so we can merge into public
and push.
git checkout public
git merge private
git push
If you wanted to keep your original 10 commits on the local private
branch, you can instead do a fast-forward merge onto the local public
branch and rebase there instead.
git checkout public
git merge private
git rebase -i origin/public
# Do the same rebase steps as above
git push
Upvotes: 7
Reputation: 632
use git rebase -i
and select squash
for your 10 commits so you'll only have one big commit rebased on your public branch.
When using -i with rebase, you'll get a text editor where you can choose how each commit will be rebased (or if it will berebased at all). Squash is the option that allow you to integrate multiple commits in a single one with this kind of syntax (from github doc, link below) :
pick 1fc6c95 Patch A
pick 6b2481b Patch B
squash dd1475d something I want to split
squash c619268 A fix for Patch B
squash fa39187 something to add to patch A
squash 4ca2acc i cant' typ goods
squash 7b36971 something to move before patch B
This will rebase 2 commits : "Patch A" will be verbatim will "Patch B" will include the changes from the next "squashed" commits.
Please see "Interactive Rebasing" in reference or the nice github doc page for details.
Upvotes: 5