Git has become so popular so quickly, it’s easy to have missed out on why you should integrate it into your coding (and writing) life. We’re going to get you quickly up to speed about why Git is special, and how to use it – and we hope to return to Git in future months to cover other ways in which Git can help you keep organised.

Git is a distributed version control system, famously written by Linus Torvalds after the BitKeeper debacle left the Linux kernel in need of a capable home. Now, through GitHub and a dozen other popular repositories that make it social to store and share code, Git is becoming
the default choice for distributed version control and source management of new projects.

On personal projects that don’t need a central repository, Git is great for keeping track of changes and experimenting with different approaches in your project using branching, giving you the choice to merge changes and/or roll them back.
To really benefit from Git you need not just a few commands on a cheat sheet, but an understanding of how it works – so we’ll touch on a few Git concepts as we go along, making it easier for you to go and find out more later.

Initial config simply consists of a few git config –global commands, which write your details into ~/.gitconfig. Without the –global switch, git config writes to ./.gitconfig so you can tailor individual repositories.

Step 04 A tree, initially

Those repositories are created where your code is; cd into a project folder and initialise your first Git repository with:

git init

A .git directory is created: you now have a working tree, and you’re now ready to commit changes to your repository. Initialisation is only done once per repository.

Step 05 Staging post

Now that you have a working repository, let’s use:

git add

…to stage the code. Passing ‘.’ as an argument adds everything in the current directory, recursively (ie including subdirectories), to the index. Now we use commit and at last our code is in the repository, and tracked by Git.

Step 06 Status

If we beaver away at writing some more code, then ask Git for a status report, it will tell us that we have made some changes that have yet to be committed. It’s good practice to commit often – Git is your source code management tool after all, so give it the changes to manage.

Step 07 Where was I?

If you haven’t committed changes for a while, git status is useful for showing just what changes you’ve made as you tunnel through Rails, for example, making changes across views, controllers and helper files. What’s changed in those files is shown by git diff (see the large screenshot on the next page).

Step 08 Undone by stages

The two-step commitment process allows one to change one’s mind at the staging step – so if you have added a file you’ve edited, but don’t after all want to commit it, then…

git reset HEAD filename

…will remove that file from staging.

Step 09 Not that one

If you’ve staged a totally new file, then

git rm --config filename

…is the better option – rm to remove a file, but –cached to just take it from staging. Here git status shows the change from stage to ‘untracked’ for the file we removed.

Step 10 Commit objects

Time to improve our understanding of what’s going on behind the scenes in Git. Each commit object contains a snapshot of the files, references to parent commit objects, and a SHA-1 name (40-character hash of parts of the commit) that uniquely identifies the commit.

Step 11 HEAD master

While the latest commit object is HEAD – and its parent is HEAD^ – that refers to the latest commit in the current branch. By default we just have a master to work on, but we can create new branches from any commit object – the above to work on an earlier version of the project’s file format.

Step 12 Branch line

git checkout gets you using another branch. It’s quite important to commit your changes before you use checkout to switch branches – otherwise some strangeness will result, such as losing all the changes you’ve made to the branch, so show some commitment and commit…

Step 13 Committed to change

Git will prompt you if you have forgotten to save before changing branch. You can use:

git checkout -- nameoffile

…to deliberately remove the uncommitted changes you have made. ‘Commits are cheap’ so keep commiting in your own branch.

Step 14 Releasable code

You can have as many branches as you like, depending on your team and strategy. One simple approach is to keep the master branch in a releasable state and commit your incremental changes to a development branch until you’re ready to merge your changes back for a new release.

Step 15 Track what’s changed

Sometimes, simply keeping track of what you’ve just done defeats the fallible human brain. What was that small change which seems to have broken something?

git diff

is your friend, showing you what has been changed but not yet staged with git add. Not the files effected (git status does that), but each line added, removed or edited.

git diff --cached

will look at the changes that have been staged but not yet committed.

Other useful diff commands to Git include

git diff HEAD^

…which shows changes since the commit previous to the latest commit.

Step 16 Branch log

Keeping track of commits for your current branch is a simple matter of running git log forthat branch. This will show the chain of commit objects since initialisation. The first few digits of the SHA-1 hash shown in log is a good reference to HEAD on the branch you’re working on, if you want to check if a colleague is using the same.

Step 17 Conflicting code

Git makes merging branches easy, but will also tell you where there is a conflict if a merge cannot take place – usually where both branches have made changes in the same place. You can also merge master into your branch to keep your tree up to date with changes there.

Step 18 Ignorance is bliss

Now, before you work with others on a project, use the .gitignore file to keep your password and local datase details out of the public repository, along with auto-saves from your text editor, notes to yourself, and anything else unnecessary for the project but in the directory.

Step 19 Push me pull you

git pull origin master will fetch the latest copy of the remote master and merge it into your local copy, thereby allowing your local copy to combine other people’s updates with your own changes. Whether you pull frequently or just after specific changes is up to you.

Step 20 Fetch

git fetch just gets the remote changes without forcing a merge. It creates a local copy for you to work from, so you can examine with git diff and make changes before merge to handle any problem conflicts you can foresee.

Step 21 Pushing code

git push is used to push changes to the remote repository. Using push.default in your config, or arguments (eg simple) to the command, you can get push to refuse to push if the upstream branch’s name is different from the local one.

Step 22 Time-saving aliases

Aliases such as gc for git commit,

ga for git add –all

and gst for git status

save valuable key strokes for frequent users. You might wish to add your own preferred aliases to your .bashrc, or download one of the macro collections to be found on GitHub.

Step 23 Try out commands

Grab some code and start trying out the commands. git clone can be used to make a local copy of a complete Git repository from elsewhere, including branches (git branch -r will show them). Those ‘Fork me on GitHub’ buttons will all be competing for your attention.

Step 24 Go use Git

Now, armed with some understanding of what Git’s about, go forth and spread thy code! Online there are plenty of tutorials on advanced Git usage and we hope to return to the topic soon in LUD, showing you many versatile uses for Torvalds’ other creation!