Inspecting Remote Data

So, what exactly did we achieve by connecting this new remote? Let's look at the list of branches:

$ git branch -va
  contact-form           56eddd1 Add new contact form page
* master                 56eddd1 Add new contact form page
  remotes/origin/HEAD    -> origin/master
  remotes/origin/master  2b504be Change headlines for about and imprint

Well, apparently not much happened: still our two local branches ("master" and "contact-form") and two items from our "origin" remote ("remotes/origin/HEAD" and "remotes/origin/master"). So why don't we see any data from our new "crash-course-remote"? Because, with the "git remote add" command, we have only established a relationship - but no data was exchanged so far.

Concept

Remote Data is a Snapshot

Git stores information about remote data (like branches, commits, etc.) in your local repository for you. However, there is no "live" connection to your remote. E.g. you will not automatically see new commits or branches that your teammates published on a remote - because you have to explicitly tell Git to update!

The information about remote branches, remote commits, etc. is only as fresh as the last snapshot that you requested. There is no "automatic" update in the background.

To update the information about a remote, you have to explicitly request this data. Most notably, a "Fetch" operation does this for you:

$ git fetch crash-course-remote
From https://github.com/gittower/git-crash-course-remote
 * [new branch]     faq-content -> crash-course-remote/faq-content
 * [new branch]     master -> crash-course-remote/master

Fetch will not touch any of your local branches or the files in your working copy. It just downloads data from the specified remote and makes it visible for you. You can decide later if you want to integrate new changes into your local project.

After updating our information about the "crash-course-remote", let's take another look at the available branches:

$ git branch -va
  contact-form           56eddd1 Add new contact form page
* master                 56eddd1 Add new contact form page
  remotes/crash-course-remote/faq-content  e29fb3f Add FAQ questions
  remotes/crash-course-remote/master       2b504be Change headlines f...
  remotes/origin/HEAD    -> origin/master
  remotes/origin/master  2b504be Change headlines for about and imprint

Now we also get information about the branches on "crash-course-remote".

Let's start working on that "faq-content" branch. Currently, however, this is only a remote branch pointer. To be able to work with this branch - to have our working copy populated with its files - we need to create a new local branch that's based on this remote branch. We're telling the "git checkout" command which remote branch we want to have:

$ git checkout --track crash-course-remote/faq-content
Branch faq-content set up to track remote branch faq-content from crash-course-remote.
Switched to a new branch 'faq-content'

$ git branch -va
  contact-form           56eddd1 Add new contact form page
* faq-content            e29fb3f Add FAQ questions
  master                 56eddd1 Add new contact form page
  remotes/crash-course-remote/faq-content  e29fb3f Add FAQ questions
  remotes/crash-course-remote/master       2b504be Change headlines f...
  remotes/origin/HEAD    -> origin/master
  remotes/origin/master  2b504be Change headlines for about and imprint

This command does a couple of things for us:

  • (a) It creates a new local branch with the same name as the remote one ("faq-content").
  • (b) It checks this new branch out, i.e. it makes it our local HEAD branch and populates our working copy with the associated files from that branch's latest revision.
  • (c) Since we're using the "--track" flag, it establishes a so-called "tracking relationship" between the new local branch and the remote branch it's based on.
Concept

Tracking Branches

In general, branches have nothing to do with each other. However, a local branch can be set up to "track" a remote branch. Git will then inform you if one branch contains new commits that the other one doesn't have:

  • If your local branch contains commits that haven't been published / pushed to the remote repository, your local branch is "ahead" of its remote counterpart branch by some commits.
  • If your teammates, on their part, have uploaded commits to the remote, the remote branch will have commits that you haven't downloaded / pulled to your local branch, yet. Your local branch is then "behind" its remote counterpart branch.

In case such a tracking relationship exists, Git will inform you about any discrepancies when performing "git status":

$ git status
# On branch dev
# Your branch and 'origin/dev' have diverged,
# and have 1 and 2 different commits each, respectively.
#
nothing to commit (working directory clean)

When creating a new local branch that is based on an existing remote branch, establishing a tracking connection is easy: simply use the "git checkout" command with the "--track" flag set.

With a new local branch "faq-content" checked out, we're ready to contribute to this feature. Let's make some modifications to the "faq.html" file that you now have on your disk (I leave the details of these changes to your imagination...):

$ git status
# On branch faq-content
# Changes not staged for commit:
#   (use "git add <file>..." to update what will be committed)
#   (use "git checkout -- <file>..." to discard changes in working 
#    directory)
#
#       modified:   faq.html
#
no changes added to commit (use "git add" and/or "git commit -a")

$ git add faq.html

$ git commit -m "Add new question"
[faq-content 814927a] Add new question
 1 file changed, 1 insertion(+)

Now it's time to share these brilliant changes we've just made with our colleagues:

$ git push
Note

On your machine, this "git push" command will not work because you don't have write access to our course remote repository. If you want to follow along and execute this command yourself, I recommend you create your own remote repository, for example on GitHub or Beanstalk.

The "git push" command uploads all the new commits from our current HEAD branch to its remote counterpart branch.

Concept

Tracking Connections Revisited

By default, the "git push" command expects us to provide it with two things:

  • (a) To which remote repository we want to push.
  • (b) To which branch on that remote repository we want to push.

The full command, therefore, looks something like this:
$ git push crash-course-remote faq-content

With the tracking connection that we've set up already, we've defined a "remote counterpart" branch for our local branch. Git can then use this tracking information and lets us use the "git push" and "git pull" commands without further arguments.

Get our Free Cheat Sheet Package

About Us

As the makers of Tower, the best Git client for Mac and Windows, we help over 80,000 users in companies like Apple, Google, Amazon, Twitter, and Ebay get the most out of Git.

Just like with Tower, our mission with this platform is to help people become better professionals.

That's why we provide our guides, videos, and cheat sheets (about version control with Git and lots of other topics) for free.