A pair of git aliases

I used to have a bunch of git aliases. git c for git commit, git co for git checkout, git st for git status, and many others. Today, I have two. Let me tell you why.

I was pairing with a colleague of mine on their computer when I realized that they didn't share the same aliases as I do. My muscle memory kept on kicking in, leaving me staring at a terminal spitting error messages like Snoop Dogg spitting bars.

$ git co
git: 'co' is not a git command. See 'git --help'.

The most similar commands are

This served as a valuable lesson. I'd hamstrung myself by making my development environment too specialized. If I only ever can work on my machine, is it really worth it?

This happened five years ago. Since then, I've accumulated exactly two git aliases. git and sync.


Sometimes I begin typing out a git command, only to be momentarily interrupted by something or someone. This usually leaves git lingering in my terminal prompt. Once I've dealt with the interruption, I retype the complete git command without thinking. git git status.

$ git git status
git: 'git' is not a git command. See 'git --help'.

The most similar command is

This happened often enough, I decided to do something about it.

$ git config --global alias.git '!git'
$ git git status
On branch master
Your branch is up to date with 'origin/master'.

nothing to commit, working tree clean


I contribute to various projects from time to time. My forks usually have two remotes, origin pointing to my fork of the original repository and upstream pointing to the original repository itself. Keeping up-to-date with upstream usually requires me to type out these commands.

$ git fetch upstream
$ git rebase upstream/master

This was fine when I just had a couple of forks and there wasn't a lot of activity. However, over time, I found myself typing this over and over again. Sometimes, I'd have to remember to stash my changes first, and then reapply them once I'm done.

This eventually led to me to the following alias.

$ git config --global alias.sync '!f() { [ "$#" -ne 1 ] && echo refname required >&2 || { git fetch "${1%%/*}" && git rebase -r --autostash "$1"; } }; f'
$ git sync upstream/master
Created autostash: 18565e3
Current branch master is up to date.
Applied autostash.

This will fetch whatever <refname> you passed to git sync, then rebase your commits onto <refname> (preserving merge commits if any). Any uncommited changes will automatically be stashed in a temporary stash entry and then reapplied automatically once the rebase is done.

VoilĂ !