git -- Distributed Version Control

Steven J Zeil

Last modified: Sep 22, 2020
Contents:

Abstract

Distributed version controls models relax the dependency upon a central repository as the keeper of the one true project.

We will look at git, a popular distributed version control system.


Sounds Like Anarchy

1 Two Levels of Committing

A Synthesis of Local and Remote

In a distributed model, a developer maintains

1.1 Push and Pull

1.1.1 Branches are Everywhere

The use of the term “merge” to describe push and pull is not an accident.

1.1.2 A Fear of Committment

The local/remote, two-Level commit approach helps resolve a common dilemma from centralized VC systems:

2 git

2.1 Where do files live?

 

2.2 Revisions


git Snapshots

A git repository contains, conceptually, a collection of snapshots (a.k.a., commit objects, a.k.a. revisions, a.k.a. versions).

Each snapshot contains


Heads

A git repository also contains a collection of heads.

These are human-assigned names for selected snapshots.

 


How shall I name thee?

Snapshots in a repository may be identified by giving

2.3 History

Common Local History Commands

2.4 Exploration

Every Local Repository is its own collection of branches

So one way to “branch” in git is to simply check out a new copy.

But sometimes we want to branch within a local repository


Branching Within a Local Repository


When Should I Commit? (Another perspective)

git users consider branches to be cheap.

So some advocate

Remember, every local copy of the repository a branch in its own right. So one way to achieve the same effect is to commit frequently in your local repository but only push to the central repository when you have something in a releasable state.

This approach delays making your unfinished code available to other members of your team. Whether this is a viable approach depends on


Merging Local Branches

3 Collaboration

Collaboration in git takes the form of interaction between your local repository and a remote repository.


Starting from a Remote Repository

If you are working with an existing remote repository

git clone remoteSpec

creates a new local repository as a copy of the remote one.


Cloning

 

Suppose that we have a remote repository with two branches and a few commit objects on each.

 

git branch --track enhanced origin/enhanced


Life after Cloning

 

Starting from this local repository, …

 

… suppose each repository adds a commit along the trunk:

Our local heads separate from the remembered positions of the remote ones.


Fetching Remote Changes

The basic command to get changes from the remote repository is git fetch

 

Remember, each repository is, in essence, a new (set of) branch(es)


Pulling Remote Changes

More commonly used than fetching is pulling, which combines a fetch and a merge

 

Starting with this remote repository…

 

…and this local one.

(Note that commits (F, G) have been made to both repositories since the clone was created.)

Then

git pull origin master

yields this new version of the local:

 


Pushing to the Remote Repository

The push command

 
If the remote repository looks like this

 
and our local repository looks like this

 

git push origin master

yields this remote repository.


Push is NOT the Opposite of Pull

It’s actually the opposite of fetch

This leads to an important restriction

The remote head must point, before a push, to an ancestor of the commit that it would point to after the push.


This Push Will Fail

 
If the remote repository looks like this

 
and our local repository looks like this,

because if it went through, we would lose access to a state already committed in the remote repository.

 


Avoiding Bad Pushes


Rebasing

Rebasing changes the parent relationship of the current head so that it appears to have been derived directly from some other selected head.

 
If we start with this and do

git rebase master

 
we get this.



from The System