Some Things Git

I've been using git for a little while now and I've been keeping notes. This is an attempt to turn those notes into a sort of cheatsheet for myself. It is by no means complete or comprehensive. My Delicious Pinboard links with the 'git' tag are also a great source of knowledge.

Start with some guides

A git Primer by Daniel Miessler

Git is Simpler Than You Think by Nick Farina

Pro Git Book by Scott Chacon

Some basic usage

I have a some bash aliases for daily use with git. I keep these in ~/.bash_aliases

alias gs="echo '' && git status && echo -e '\n# Available branches' && git branch"
alias gd="git diff"
alias gl="git log"

Working in branches

In general I find that it's best to do one task in one branch. These are 'topic branches'.

# you can find out what branches there are
git branch

# create a new branch
git branch new-branch-name

# and checkout that branch
git checkout new-branch-name

When you create a new branch, it's from your current working branch. Keep this in mind!

# create a new branch with uncommitted changes
git checkout -b new-branch-name

# delete a branch, -D will force delete ignoring errors
git branch -d delete-branch-name

Branches are for merging. For example, you work in the branch 'topic', and then merge those changes into your 'master' branch

# commit your work in branch 'topic'
git checkout topic
git commit -a -m 'a commit made in the topic branch'

# switch to 'master' branch and merge changes from 'topic'
git checkout master
git merge topic

Branches can be pushed to and deleted from remote repos

# push a branch to a remote branch
git push remote branch

# delete a branch from a remote
git push origin :branch

And you can delete local branches where the remote branch has been deleted

# a 'dry run' will show what is to be removed without doing so
git remote prune origin --dry-run

# to perform the prune
git remote prune origin

This gets into a whole area of discussion, git branching models. 'A successful Git branching model' by Vincent Driessen should get you started.

Getting some work done

Take a look at what you can do with git stash. I personally shy away from using the stash and think of it like this : never stash anything unless you know exactly when you will unstash it.

# stash something
git stash

# unstash it
git stash pop

When planning merges and such this is handy too. Be sure to read up on the HEAD as well.

# diff between two branches
git diff branch1..branch2

# so check what your merging
git diff topic..master
git merge topic

You may even find yourself in the position of having to add a new, empty initial commit.

# first you need a new empty branch; let's call it `newroot`
git checkout --orphan newroot
git rm -rf .

# then you apply the same steps
git commit --allow-empty -m 'root commit'
git rebase --onto newroot --root master
git branch -d newroot

# you shouldn't do this if you don't understand what it does
git push origin --force

Tags and Releases

Tags are useful for marking a particular "point" in the codebase. This works well for a release version. Having the tags then makes it easy to download the repo (on the production webserver) and then checkout that tag.

# add a new tag
git tag -a new-tag -m 'a description of the tag'

# you can view the tags
git tag

# with more details
git tag -l -n1

# share a tag
git push origin tag-name

# checkout a tag (will detach HEAD)
git checkout tag-name

# or checkout a tag in a branch
git checkout -b branch-name tag-name

# delete a tag
git tag -d tag-name

# delete tag from origin
git push origin :refs/tags/tag-name

Rebasing and cherry picking

With rebasing you can take all the changes that were committed on one branch and replay them on another one. You can also do an 'interactive rebase'.

# rebase from master
git rebase master

# interactive rebase to squash previous 4 commits
git rebase -i HEAD~4

And then there's cherry pick, which is what it sounds like.

# checkout the branch you want commits from and find them
git checkout cherrypick-branch-name
git log --pretty=oneline

# then switch into the target branch and cherrypick w/ commit id
git checkout -b new-branch-name origin
git cherry-pick 04566389idae36651daf3dfa117a1088d594632370

Some final thoughs

I'm using Indefero Gogs for a repository server.

GitGutter for vim is awesome.

The Git Homepage explains basically everything.

published on 2013-08-13
updated on 2017-11-13