Push & Pull

1.1 the Git fetch

Note: o/master is origin/master

The equivalent of a Git remote repository actually boils down to two things: transferring data to and retrieving data from a remote repository. Now that we can sync with the remote repository, we can share any updates that Git can manage (thus sharing code, files, ideas, love letters, and so on).

In this lesson we will learn how to fetch data from a remote repository — the command is called Git fetch, as its name implies.

Before explaining Git Fetch, let’s take a look at the instance. Here we have a remote repository that has two commits that we don’t have in our local repository.

With git fetch, C2 and C3 are downloaded to the local repository and the remote branch O/Master is updated to reflect this change:

Git Fetch does the only but important two steps:

  • Download the commit record missing from the local repository from the remote repository
  • Update the remote branch pointer (e.goirgin/master)

Git fetch does not change the state of your local repository. It doesn’t update your Master branch or modify files on your disk.

This is important to understand, because many developers mistakenly believe that after git fetch is performed, their local repository is synchronized with their remote repository. It may have downloaded all the data it needs to do this, but it hasn’t modified your local files. We’ll look at the command that does this later in the lesson πŸ˜€

1.2 the Git pull

Now that we know how to fetch remote data with Git fetch, let’s learn how to update these changes to our work.

There are many ways to do this – you can merge remote branches just like you merge local branches when there is a new commit in the remote branch. This means you can execute the following command:

  • git cherry-pick origin/master
  • git rebase origin/master
  • git merge origin/master
  • , etc.

In fact, because the process of grabbing updates and merging them into a local branch is so common, Git provides a special command to do both. It’s called Git pull.

git pull === git fetch + git merge

1.3 the Git push

The behavior of git push without any parameters is related to a git configuration called push.default. The default value depends on the version of Git you are using, but in this tutorial we are using upstream. It’s not a big deal, but it’s a good idea to check this configuration before pushing in your project.

To simulate this, the local branch is on the left and the remote branch is on the right

With git push:

1.4 Common Git workflow 1

Now we know how to pull commit records from other places and how to push our own changes. It doesn’t seem difficult, but why is it so confusing? The difficulty comes from the deviation in remote library commit history. Before we get into the details of this problem, let’s look at an example…

Let’s say you clone a warehouse on Monday and start working on some new feature. By Friday, your new feature development is tested and ready for release. But — oh dear! Your colleague wrote a bunch of code this week and changed a lot of the apis used in your features, making your new features unusable. But they’ve already pushed those commits to the remote repository, so you’re working on code based on the old version of the project that doesn’t match the latest code from the remote repository.

In this case, Git push doesn’t know what to do. If you do git push, should Git get the remote repository back to where it was on Monday? Or simply add your code to the new code, or simply ignore your commit because it’s out of date?

Git will not allow you to push changes because there is so much uncertainty in this case. It actually forces you to merge remote up-to-date code before you can share your work.

Git push is not available as shown below

So how to solve this problem? Quite simply, all you need to do is base your work on the latest remote branch. There are many ways to do this, but the most straightforward way is to tweak your work through Rebase. Let’s go ahead and see how to rebase!

Git fetch git rebase origin/master git pushCopy the code

The results are as follows:

Of course, in addition to rebase, you can also use merge, as in the above example:

Git pull origin/master git pushCopy the code

The results are as follows:

1.5 rebase 还是 merge?

In the development community, there is a lot of discussion about Merge versus Rebase. Here are the pros and cons of Rebase:

  • Pros: Rebase keeps your commit tree clean, with all your submissions on one line

  • Cons: Rebase modifies the history of the commit tree

For example, committing C1 can be rebase to C3. This looks like work in C1 takes place after C3, but it actually takes place before C3.

Some developers prefer merge because they prefer to keep commit history. Others, however, may prefer a clean commit tree and thus prefer Rebase. Different people have different views on the same thing. πŸ˜€

1.6 Common Git workflows ii

For a more complex example, how do I convert Figure 1 to Figure 2?

The solution steps are as follows:

git checkout master
git pull --rebase
git checkout side1
git rebase master
git checkout side2
git rebase side1
git checkout side3
git rebase side2
git checkout master
git rebase side3
git push
Copy the code

This may seem like a lot of steps, but don’t panic, there’s actually a simpler way to write it:

git fetch
git rebase origin/master side1
git rebase side1 side2
git rebase side2 side3
git rebase side3 master
git push
Copy the code

Of course, we can also use merge, but the resulting commit timeline is completely different:

git checkout master
git pull
git merge side1
git merge side2
git merge side3
git push
Copy the code