73

I don't understand the difference between git pull --rebase and git rebase, without any other options.

I don't understand if they are safe, a good practice, or very dangerous.

Can I break the history of commits by doing a git pull --rebase in local?

bflemi3
  • 6,698
  • 20
  • 88
  • 155
sab
  • 4,352
  • 7
  • 36
  • 60

3 Answers3

42

I don't recommend rebasing at all but just for private branches. By private I mean branches that you're pretty sure only you have pulled.

A rebase changes the starting point of the branch to some newer commit, thus merging all the commits to that point. This could lead to merge conflicts to people that had in their repository the old branch base. I would recommend plain merge always and leave rebasing only for certain situations (feature branches, for example).

Regarding your question:

  • git rebase rebases the branch you want.
  • git pull --rebase performs a fetch + rebase in the branches you pull. Normally a pull would fetch + merge.
Luis
  • 2,833
  • 3
  • 27
  • 41
  • 2
    So, do a git pull --rebase is safe? – sab Jun 27 '16 at 09:41
  • Safe in which sense? A rebase changes the starting point, the difference between one or the another is that git pull --rebase does a massive rebase. I wouldn't recommend rebasing in shared branches, so I wouldn't recommend git pull --rebase. Do a simple git pull instead. – Luis Jun 27 '16 at 13:18
  • 1
    The help for git pull mentions this under the --rebase option: "When true, rebase the current branch on top of the upstream branch after fetching. If there is a remote-tracking branch corresponding to the upstream branch and the upstream branch was rebased since last fetched, the rebase uses that information to avoid rebasing non-local changes." If you run a git fetch and then a git rebase, you don't get remote changes merged into your branch, as far as I can see. You do with a git pull --rebase. – dnuttle Aug 05 '19 at 14:20
  • Not clear. What so special about `fetch`? Why did they make distinction like that? – Green Nov 05 '19 at 09:06
  • In that case, what is the difference between `git rebase...` and `git fetch ...; git rebase...` ? The @everton answer clarifies a bit: https://stackoverflow.com/a/38077401/384049 – iJames Sep 02 '22 at 17:42
31

git pull --rebase is a shorthand for git fetch and then a plain git rebase, as opposed as to the default git merge. The practical difference is that applying only the latter would not fetch any new commits from your remote prior to rebasing your code on top of, as it would only take into account what your local repository's already aware of.

It's also worth mentioning that merging conflicts would appear in the same way as a regular git pull.

everton
  • 7,579
  • 2
  • 29
  • 42
  • 1
    From what I see, a git pull --rebase does more than a git fetch and a git rebase. Those two will not merge in any changes on the remote, but git pull --rebase will. So if you do git pull --rebase master, all changes on the remote for the master branch will be merged into your branch, but your local master branch will not be touched. – dnuttle Aug 05 '19 at 14:30
  • Running `git pull --rebase` causes the post-merge hook to execute. Running `git fetch` and then `git rebase` does not execute the post-merge hook. So the first is not a shorthand for the other. What I am still trying to understand is if there are any more differences between the two approaches. Either accidental, or semantic. – Noam Gal Jul 15 '20 at 05:50
  • 3
    OK, this post explains some differences between `pull --rebase` and `fetch` + `rebase` -https://gitolite.com/git-pull--rebase – Noam Gal Jul 15 '20 at 06:16
  • the gitolite.com/git-pull--rebase explained everything, the git pull --rebase is a favored when working on a features/private branches to merge/rebase (the so-called public/protected branches) – mochadwi Jun 21 '21 at 11:31
0

Trial to better explain the difference between git pull --rebase and git rebase incorporating the comments of @noam-gal and @dnuttle

Simple situation: If the history of the upstream wasn't rewritten, git pull --rebase is git fetch + git rebase.

Advanced situation: If the history of the upstream was rewritten (f.ex. due to a rebase or amend of already pushed commits), git pull --rebase is git fetch + a rebase of the local changes on the remote branch (i.e. git rebase --onto <default_remote>/<current_branch> a <current_branch>, with a the most recent upstream commit that is a parent of your local current branch). Advantage of this approach is that changed upstream commits don't result in conflicts with the old version of these commits.

References

When true, rebase the current branch on top of the upstream branch after fetching. If there is a remote-tracking branch corresponding to the upstream branch and the upstream branch was rebased since last fetched, the rebase uses that information to avoid rebasing non-local changes.

m7913d
  • 10,244
  • 7
  • 28
  • 56