I\'m working on a local branch \"BDD-local\" and would like to get the changes from other developers. The other developers are using their own branch and once they are happ
A git pull
is going to run a git fetch
and then a git merge
. If you want to bring your local repository up to speed with a remote repository that is what you would run.
A git fetch
is going to import commits from a remote repo without merging them, which gives you the opportunity to review them before integrating.
git pull
is the same as git fetch
+ git merge
The command
git pull <remote> <branch>
is really just the same as
git fetch <remote>
git merge <remote>/<branch>
So there is no practical difference between
git pull origin master
and
git fetch origin
git merge origin/master
As stated in the official Linux Kernel git pull documentation:
In its default mode,
git pull
is shorthand forgit fetch
followed bygit merge
FETCH_HEAD
.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.
fetch, merge, and pull
git fetch
and git merge origin/master
will fetch & integrate remote changes. Let me explain a common scenario. origin/master is at C. Someone pushed D. You worked on E & F. Note that you will not see D in your local repository until you run git fetch
.
origin/master
v
A-B-C-E-F < master
\
(D) < master on remote
Now you run git fetch
. Now you can see D, and origin/master is updated to match the remote repository that it's tracking.
A-B-C-E-F < master
\
D < origin/master, master on remote
Now you run git merge
, giving you this:
A-B-C-E-F
\ \
D---G < master
^
origin/master, master on remote
So now you've integrated your changes on master (E, F) with the new commits on origin/master (D).
git pull
is simply a shortcut for the above steps.
git merge without fetching
Running git merge origin/master
without the git fetch
is pointless. Without a git fetch
, your local repository is unaware of any potential changes on the remote repository and origin/master will not have moved. So you're at this state, where D is only on the remote and not present locally:
origin/master
v
A-B-C-E-F < master
\
(D) < master on remote
Since your local repository does not have D, a git merge origin/master
will simply yield:
Already up-to-date.
Because hey, as far as your local repository is concerned, master already has everything in origin/master.
What's best?
None of the above. :)
git fetch
git rebase origin/master master
or a shortcut, git pull -r
, but personally I prefer to see the changes before I rebase.
This will replay your changes on master (E, F) on top of origin/master (D) without a yucky merge commit. It yields:
A-B-C-D-E'-F' < master
^
origin/master, master on remote
Note how everything is in a single line, you're ready to push, and the history doesn't look like a friendship bracelet.
One warning - never rebase any commits that have already been pushed. Note that E & F became E' & F' after rebasing. The commits are entirely rewritten, with a new SHA and everything. If you rebase commits that are already public, developers will have their history re-written for them when they pull. And that's awful, and everyone will give you evil eyes and shun you.