Beliebte Suchanfragen

Cloud Native

DevOps

IT-Security

Agile Methoden

Java

//

Get the Most out of Git Aliases

22.6.2017 | 4 minutes of reading time

If you are like me and use the Git command-line a lot, you will probably grow your own list of Git aliases sooner or later. This article won’t be about simple standard aliases which most of us will probably have anyways (ci -> commit, co -> checkout, etc.). I’d rather like to show some advanced tricks you may find useful.

Overcome the Limitations

Simple Git aliases are quite limited. Git replaces the command you typed with whatever you alias it for. This means you cannot use positional parameters or call external programs. However, there are ways around this. One way would be to create custom Git commands. These are separate files. They must be on your PATH, start with git-, and not have a file extension. This is useful for more extensive scripting. Most of the time, it is just easier to stick with normal Git aliases. The trick is to start the alias with an exclamation mark ‘!‘. Git will then shell out the command, i. e. you can use shell expansion, pipes, etc.

Make the Git Log Nicer

The standard Git log command is not really that useful. It is very verbose creating multiple lines per commit. It is fairly straightforward to create your own alias for a better log output.

1l = log --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%ci) %C(bold blue)<%an>%Creset'

That was easy. But my actual point is that you can now build upon this alias and create further aliases that are based on it. Here are two examples that enhance the output to draw a graphical representation.

1# graphical representation for all refs	 	 
2lga = !git l --graph --all
3 
4# graphical representation for branches only	 	 
5lgb = !git l --graph --branches

The following alias shows incoming commits for your current branch. The branch must be configured to track a remote branch for the special ref @{upstream} to work. Conversely, the same is possible to show outgoing commits you have not yet pushed.

1# log incoming commits
2li = !git l HEAD..@{upstream}
3 
4# log outgoing commits
5lo = !git l @{upstream}..HEAD

Make Branch Handling Easier

From time to time, you may have to clean-up your repo removing outdated branches. Here’s a few tricks to better identify them. You can run git branch -avv to list branches and show the latest commit messages. But this does not tell you how old they are and who made the last commit on the branch. In order to fix that we first need an alias that lists refs sorted by date and also displays the relative date, the author, and the subject.

1refs = for-each-ref --sort=-committerdate --format='%(color:red bold)%(refname:short)%(color:reset) %(color:yellow)%(committerdate:relative)%(color:reset) %(color:magenta bold)%(authorname)%(color:reset) %(color:green)%(objectname:short)%(color:reset) %(contents:subject)'

Based on this alias, we can now create two more aliases, one to show local branches and another one to show remote branches.

1# list all local branches sorted by commit date (lbs = local branches sorted)
2lbs = !git refs refs/heads
3 
4# list all remote tracking branches sorted by commit date (rbs = remote branches sorted)
5rbs = !git refs refs/remotes

Here’s a sample screenshot of a git rbs output:

The following alias is useful for listing branches that track remote branches which no longer exist. This can happen when a pull request is merged and you still have your local branch around. In most cases, these branches can just be deleted, which can also be done with an alias.

1# list outdated branches that track a branch which no longer exists
2lob = !git branch -vv | grep ': gone' | cut -d ' ' -f 3
3 
4# delete outdated branches
5dob = !git lob | xargs git branch -D

Make Your Open-source Life Easier

If you are like me and enjoy contributing to open-source projects, you can make your life a little bit easier. Being a member of the Helm charts maintainers team, I test pull requests on a regular basis. This requires fetching them in the first place. Of course, I don’t want to clone the PR owner’s repo each time. That’s unnecessary because PRs also live in special branches in the target repo which Github does not really show you. The following alias fetches a PR and checks out its HEAD directly. You need to pass the pull request ID as parameter. You’ll then end up with a detached HEAD but that’s perfectly fine in this case.

1# fetch and checkout a Github pull request
2fp = "!f() { git fetch upstream "pull/$1/head" && git checkout FETCH_HEAD; }; f"

The alias is based on the assumption that a remote named upstream exists. This is how I configure the repos I contribute to. Here’s what this looks like in my .git/config for the Helm Charts repo:

1remote.upstream.url=git@github.com:kubernetes/charts.git
2remote.upstream.fetch=+refs/heads/*:refs/remotes/upstream/*
3remote.origin.url=git@github.com:unguiculus/charts.git
4remote.origin.fetch=+refs/heads/*:refs/remotes/origin/*

Here comes one last goodie. When working with open-source repos you may want to configure an e-mail address other than that in your global Git config. However, it is easy to forget that. In case you have committed something with the wrong address, here’s an alias that allows you to fix the commit (after fixing the e-mail address in the repo’s local Git config, of course).

1# re-commit resetting the author and re-using the commit message
2rci = "!f() { ref=$(git rev-parse HEAD); git reset --soft HEAD^; git commit --reset-author -C "$ref"; }; f"

share post

Likes

0

//

More articles in this subject area

Discover exciting further topics and let the codecentric world inspire you.

//

Gemeinsam bessere Projekte umsetzen.

Wir helfen deinem Unternehmen.

Du stehst vor einer großen IT-Herausforderung? Wir sorgen für eine maßgeschneiderte Unterstützung. Informiere dich jetzt.

Hilf uns, noch besser zu werden.

Wir sind immer auf der Suche nach neuen Talenten. Auch für dich ist die passende Stelle dabei.