368

I started using git sometime back and do not fully understand the intricacies. My basic question here is to find out the difference between a git pull and git pull --rebase , since adding the --rebase option does not seem to do something very different : just does a pull.

Please help me with understanding the difference.

3

5 Answers 5

377

git pull = git fetch + git merge against tracking upstream branch

git pull --rebase = git fetch + git rebase against tracking upstream branch

If you want to know how git merge and git rebase differ, read this.

Sign up to request clarification or add additional context in comments.

3 Comments

It's worth noting that saying git pull --rebase is the same as git fetch and git rebase is basically how it is, but it's not exactly semantically equivalent. There are some differences, some of which are explained here. gitolite.com/git-pull--rebase
It's what I would call a "convenient lie," to borrow a phrase from Scott Meyers. It's a good way to explain it regardless.
Very briefly. I can't understand the difference. What so important about fetch?
262

Sometimes we have an upstream that rebased/rewound a branch we're depending on. This can be a big problem -- causing messy conflicts for us if we're downstream.

The magic is git pull --rebase

A normal git pull is, loosely speaking, something like this (we'll use a remote called origin and a branch called foo in all these examples):

# assume current checked out branch is "foo" git fetch origin git merge origin/foo 

At first glance, you might think that a git pull --rebase does just this:

git fetch origin git rebase origin/foo 

But that will not help if the upstream rebase involved any "squashing" (meaning that the patch-ids of the commits changed, not just their order).

Which means git pull --rebase has to do a little bit more than that. Here's an explanation of what it does and how.

Let's say your starting point is this:

a---b---c---d---e (origin/foo) (also your local "foo") 

Time passes, and you have made some commits on top of your own "foo":

a---b---c---d---e---p---q---r (foo) 

Meanwhile, in a fit of anti-social rage, the upstream maintainer has not only rebased his "foo", he even used a squash or two. His commit chain now looks like this:

a---b+c---d+e---f (origin/foo) 

A git pull at this point would result in chaos. Even a git fetch; git rebase origin/foo would not cut it, because commits "b" and "c" on one side, and commit "b+c" on the other, would conflict. (And similarly with d, e, and d+e).

What git pull --rebase does, in this case, is:

git fetch origin git rebase --onto origin/foo e foo 

This gives you:

 a---b+c---d+e---f---p'---q'---r' (foo) 

You may still get conflicts, but they will be genuine conflicts (between p/q/r and a/b+c/d+e/f), and not conflicts caused by b/c conflicting with b+c, etc.

Answer taken from (and slightly modified):
http://gitolite.com/git-pull--rebase

5 Comments

This is the best answer. You might want to change the final result to a---b+c---d+e---f---p'---q'---r' (foo) since rebase changes hashes.
This answer was copied and pasted verbatim from gitolite.com/git-pull--rebase and should include attribution per the license on that page.
This is a great explanation. But I had a situation, where I had commit A, and I sent a PR to the upstream repo which got accepted. Then when I did git pull --rebase against the upstream repo, I didn't get a new A' commit on top of the pulled upstream repo. In fact no A' existed at all. Is this because A was merged into the system? Or is it because there was no difference between the upstream and my rebased onto version?
I'm currently going through the Git tutorial and was using this response to further understand a git pull --rebase. But one thing that confuses me in this hypothetical situation is that the upstream maintainer has changed project history that has already been pulled into local developer's repositories. Isn't this just bad practice in general? If he wanted to squash commits/rewrite history, it should have been done before integrating it into the central repository to avoid these type of conflicts.
Not long after this answer was originally posted, git rebase was modified so that it now also performs the additional steps done by git pull --rebase.
50

Suppose you have two commits in local branch:

 D---E master / A---B---C---F origin/master 

After "git pull", will be:

 D--------E / \ A---B---C---F----G master, origin/master 

After "git pull --rebase", there will be no merge point G. Note that D and E become different commits:

A---B---C---F---D'---E' master, origin/master 

3 Comments

isn't it A---B---C---D'---E'--F ?
@prgmrDev Why would D and E be inserted before F?
Isn't it exactly what git rebase does? But we're talking about git pull --rebase. And they are different things.
10

In the very most simple case of no collisions

  • with rebase: rebases your local commits ontop of remote HEAD and does not create a merge/merge commit
  • without/normal: merges and creates a merge commit

See also:

man git-pull

More precisely, git pull runs git fetch with the given parameters and calls git merge to merge the retrieved branch heads into the current branch. With --rebase, it runs git rebase instead of git merge.

See also:
When should I use git pull --rebase?
http://git-scm.com/book/en/Git-Branching-Rebasing

3 Comments

And in case of collisions ?
You will get asked to resolve them manually and then - continue with rebase:git sdd modified-file; git rebase --continue or merge:git add modified-file; git commit; where modified-file is your local file you modified manually/mergetool
What so special about fetch? Why did they created two rebase flows? 1) git rebase and 2) git pull --rebase?
9

For this is important to understand the difference between Merge and Rebase.

Rebases are how changes should pass from the top of hierarchy downwards and merges are how they flow back upwards.

For details refer - http://www.derekgourlay.com/archives/428

1 Comment

I think that your answer offers a much simpler explanation that is not obvious on the rest of the answers above. Thanks.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.