Paebbels
Paebbels

Reputation: 16249

How to fix alignment problem in git log --graph

I'm using the following alias to render my git commit history on console if no GUI is available:

$ git config alias.treex
log --color --graph --pretty=format:'%C(cyan)%h%Creset - %C(cyan)%ad%Creset %<(80,trunc)%s   %C(cyan)%>(20,trunc)%an - %Cgreen%>(12)%cr%Creset' --date=format:'%d.%m.%Y %H:%M' --abbrev-commit --all

While the format string uses align and fixed size string formats like %<(80,trunc)%s, the graph rendered by git log --graph destroys the alignment:

Git treex result.
(click to enlarge)

How to fix the broken alignment cause by the graph itself?

Upvotes: 3

Views: 1057

Answers (2)

millokeller
millokeller

Reputation: 282

Shifting the %h placeholder for alignment

As axiac previously mentionend you can constrain the width of the first field. For example, if you add %>|(16) to the beginning of your formatting definition you can shift the abbreviated commit hash (%h) to finish at least at the 16th column. If you subtract the 7 digits of %h and an additional whitespace character you will give the graph a scope of 8 digits.

Your original git log history format: Unaligned git log history

A more aligned version by adding %>|(16) for %h: Aligned git log history

Adding a length argument

As axiac also mentioned, this solution will face a problem. Once your graph exceeds the lenght of 8 characters, due to a project containing many parallel branches, your log entries will get shifted even more. You would have to adjust your alias according to the current Git project situation. Luckily there is a trick for powerful Git aliases. With this trick you can pass an argument to your alias that sets the number of shifted columns.

Calling your alias with the paramater 30 then shifts your Git log history entries by 22 columns: Aligned git log history with argument

Set a default value for the length argument

Now, it may not be your intention to pass the number of columns every single time you call your alias. This link explains how to set a default parameter. This way your alias refers to the default value once called without an argument. Once we are at it, we can correct the deviation of 8 digits directly inside the alias. Thereby, the passed argument directly corresponds to the columns actually shifted.

Final alias

Your final Git alias accepting an argument to shift the Git log entries by x columns with a default shift of 8 digits:

$ git config --global alias.treex
!f() { x=${1-16}; length=`expr $x + 8`; git log --color --graph --pretty=format:"%>|($length)%C(cyan)%h%Creset - %C(cyan)%ad%Creset %<(80,trunc)%s   %C(cyan)%>(20,trunc)%an - %Cgreen%>(12)%cr%Creset" --date=format:%d.%m.%Y; }; f

Upvotes: 4

axiac
axiac

Reputation: 72336

Instead of %<(80,trunc)%s that tells git log to render the subject on 80 characters you can use %<|(110,trunc)%s that tells it to render the subject until it reaches the 110th column of the output. This way the next field after the subject starts at the 111st column and the order is restored.
(110 is approximately the original 80 characters you want for the subject + the sizes of the columns before it (%h = 7 characters, %ad = 16 characters) and the delimiter characters you put between them.)

Of course you can use a different value. You can also try to constraint the width of the first field (%h) to get all the other fields aligned but it won't align properly on the sections of the history that contain a lot of branches; the %s field is large and uses enough columns to accommodate two dozens of concurrent branches.

The format is described in the documentation of git log right under the <() format and it is present in all versions of the documentation page (that unfortunately starts with 2.3.8). If you are using an older Git version, it is possible that the format is not available for you. The best advice in this situation is to update your Git to a more recent version.

Upvotes: 4

Related Questions