This post lists all the Git command that I use frequently.

Pro Git is an excellent book on how to use Git.

Clone a repository

# Clone from an existing ("bare") remote repo.
$ git clone git://<repo-url>  <local-directory>
$ git clone http://<repo-url> <local-direcotry>

Create a bare repository

# initialize a bare repository
$ cd <directory>
$ git init --bare

# turn an existing "non-bare" repository into a "bare" one
$ git clone --bare -l <non-bare-repo> <new-bare-repo>

Set user information

# Set user info globally (applicable on all the Git repos on this computer)
$ git config --global  "<global username>"
$ git config --global "<global user email>"

# Check global user info
$ git config --get --global
$ git config --get --global

# Set user info locally (per repo)
$ cd <local-repo>
$ git config --local  "<repo-specific username>"
$ git config --local "<repo-specific user email>"

# Check local user info
$ git config --get --local
$ git config --get --local

Check and set end-of-line setting

$ git config --global --get core.autocrlf  # Should be "true"
$ git config --global core.autocrlf true   # Set it to "true"

Undo changes

# restore the entire working tree to the last committed state
$ git reset --hard HEAD

# unstage one staged file
$ git reset HEAD <file-name>

# restore one untracked file
$ git checkout --   <file-name>
$ git checkout HEAD <file-name>

Push changes to remote repository

# prepare the http.proxy config: check, add, or unset
$ git config --get http.proxy
$ git config --global --add http.proxy <proxy>
$ git config --global --unset http.proxy

# check branches
$ git branch -v

# check remotes
$ git remote -v

# add remote repo (if not yet added)
$ git remote add origin <repo>

# push to remote
$ git push origin master

Show changed filenames in a commit

$ git diff-tree --no-commit-id --name-only -r <commit-SHA>

Create tags

# list available tags in alphabetical order (the order has no real importance)
$ git tag

# show details about a tag
$ git show <tag-name>

Git uses two main types of tags: lightweight and annotated.

  • A lightweight tag is just a pointer to a specific commit (very much like a branch that doesn’t change).
  • Annotated tags are stored as full objects in the Git database. They’re checksummed; contain the tagger name, e-mail, and date; have a tagging message; and can be signed and verified with GNU Privacy Guard (GPG).

In general, annotated tags are recommended as they contain all this information. Lightweight tags are used for creating temporary tags.

# create an annotated tag (with the '-a' option)
$ git tag -a <tag-name> -m "<message>"

# tag a specific commit
$ git tag -a <tag-name> -m "<message>" <commit-SHA>

# create a lightweight tag (do not supply any option)
$ git tag <tag-name>

By default, the git push command doesn’t transfer tags to remote servers. Tags need to be pushed explicitly.

# push a tag to the 'origin' remote server
$ git push origin <tag-name>

# transfer all tags to the 'origin' remote server
$ git push origin --tags

Rename a remote tag

To renaming an existing tag to a new name:

$ git tag new-tag old-tag             # Create new-tag as an alias of old-tag (locally)
$ git tag -d old-tag                  # Delete old-tag (locally)
$ git push origin :refs/tags/old-tag  # Delete old-tag from remote repository
$ git push --tags                     # Push tags to remote repository (thus create new-tag)

Then for all other local repositories, to synchronize tags with remote repository:

$ git tag -l | xargs git tag -d  # Delete all tags from local repository
$ git fetch                      # Get tags back from remote repository

Work with local branches

Local branches can be used by a single developer, when collaboration is not needed. A typical workflow is:

Step 1: Create and checkout a local branch from master

# Make sure we are at master
$ git branch
* master

# Create and checkout a local branch from master.
$ git check -b local-dev

Step 2: Work on the local branch – all changes are committed in this local branch.

Step 3: As the master branch might also evolve, keep the local branch updated.

To merge changes from master into the local branch, git rebase is preferred to git merge.

# Update the master branch.
$ git checkout master
$ git pull

# Merge (via git rebase) changes from master back into the local branch.
$ git checkout local-dev
$ git rebase master

Step 4: Once the development is done, merge changes into master, and push to the remote repository.

If the local branch is synchronized with master via git rebase, merging from the local branch into master should simply be a fast-forward merge.

$ git checkout master
$ git merge local-dev
$ git push

Step 5: Final step: delete the local branch.

$ git branch -d local-dev

Create and apply patches

To create patches from one repo, start by listing the changelog:

$ git log --pretty=oneline
d241dcf39ed2a3ff58dbba0c12489038c2019215 Added content in homepage.
b537f59855019c03e3f72422cd033d62022f5240 Committed first version of my Jekyll site.
90d33f4a800253d2f4fa39950d7652f9b4fde5dc Initial commit

To create patches for the last two commits, note down the SHA of the commit right before (only several first letters will be enough) and use it as a starting point:

$ git format-patch 90d33f4a80

This will generate two patch files, each containing one commit.

To create a single patch file with all changes in it:

$ git format-patch 90d33f4a80 --stdout > all-changes.patch

Copy these patch files to another repository where the patches need to be applied:

# To check what files are affected by one patch:
$ git apply --stat 0001-Committed-first-version-of-my-Jekyll-site.patch

# To see if the patch can be applied smoothly:
$ git apply --check 0001-Committed-first-version-of-my-Jekyll-site.patch

# If nothing is returned from the previous command, apply it:
$ git apply 0001-Committed-first-version-of-my-Jekyll-site.patch

# If there are errors, we can still apply just the parts that will work.
# Following command will apply the patch while generating *.rej files:
$ git apply --reject 0001-Committed-first-version-of-my-Jekyll-site.patch