Git Blame

0
31

Table of Contents

Git blame is a command used to check which developer authored each line of a particular commit file and how many revisions it’s had. The output of Git blame displays a line-by-line readout indicating the line number, the most recent commit ID for each change, the author, and the date and time information. The idea is that the team can track changes and attribute them to an author if problems arise from that commit. Git blame does not reveal information about lines that have been deleted or replaced.

When to Use Git Blame

Git blame can reveal who last changed the code and when they changed it.

Git blame is a great tracking tool for teams. Unexpected errors can be introduced in many ways and at many points in the development process. Because of the distributed and collaborative nature of Git version control, it can be impossible to keep track of who made what changes. That’s where git blame can step in to help.

How to Use Git Blame

Most use cases of Git blame center around an error or bug introduced by someone working on the project, making changes and commits.

When you realize your project has a bug because it’s not working correctly, you need to identify the problematic commit before you can figure out who introduced it.

Start by using git bisect to track down the commit that introduced the bug. Git bisect uses a binary search algorithm to efficiently search through commits, halving the potential commits with each bisect. To get started enter git bisect start. Now enter the last known good commit and the known bad commit (usually the HEAD) as follows:

git bisect bad <commit hash> 
Git bisect good <commit hash>

Git will begin bisecting. You’ll need to compile each commit after it’s been checked out by Git bisect, to verify if it’s good or bad. The process will continue until there are no commits left to verify. Then Git will output:

<commit hash> is the first bad commit

Once the commit that introduced the bug has been identified, using git diff reveals the changes made to that commit. There may be multiple authors making changes to the same commit. Looking through the git diff output reveals what was removed or added for each line. To get started plug the last known good commit hash and the bad commit hash that you found with git bisect, into the git diff command:

$ git diff <good commit hash><bad commit hash>

Examine the output to figure out which lines introduced the bug.

Now that you’ve narrowed down the specific bad commit and located which lines were last edited, it’s time to use git blame to identify who made the changes for the lines that introduced the error. The basic git blame command format is as follows:

git blame <filename>

While the basic git blame output format displays commit hash, author name, date and time, line number, and line content:

Commit Hash (Author name Date Time Line Number) commit message

Here is an example with the format filled in with dummy data:

1a2bc34d (Jane Doe 2022-02-02 01:11:11 -0800 1) this is an example

In the example below, we’re looking at a basic Python calculator program and calling git blame to look at the revision history. A reminder that this is a line-by-line output of each revision commit hash, author, timestamp, line number, and code change. In this example, you’ll notice multiple people are working to create a calculator, but someone introduces a mistake that causes the calculator to not work properly:

$ git blame calculator.py

0a2012f  (John Doe  2022-05-05  10:23:10 +0100 1) #program makes a simple calc
85c0354 (John Doe    2022-05-06  01:20:10 +0100 2) #function for adding 2 num
85c0354 (Tom Train   2022-05-06  05:30:20 +0100 3) def add (x, y):
85c0354 (Tom Train   2022-05-06  08:45:05 +0100 4) 	return x + y
85c0354 (John Doe   2022-05-06  08:49:32 +0100 5) #function for subtracting 2 num
cd918fd (Jane Smith  2022-05-08  10:15:10 +0100 6) def subtract (x, y):
cd918fd (Jane Smith  2022-05-08  11:00:20 +0100 7) 	return x + y
cd918fd (John Doe     2022-05-10  08:40:50 +0100 8) #function for multiplying 2 num

You’ve already identified the problematic commit to be 85c0354 by using git blame. From git diff, you know that someone coded the subtraction function to add instead of subtract. Now with git blame, you know that Jane Smith was the original author that coded this function. This is a simple example of a very obvious error, demonstrating how a bit of blame can help your team.

Git Blame Options

To preview the git blame command options, just type in git blame with no file extension or modifiers, or you can use the git help blame command. There’s a wide range of options, but we’ll cover the most commonly used below:

git blame -w – Simplifies output, so whitespace changes made by an author aren’t listed in the revisions
git blame -c – Identifies lines that are copied from other files and displays the original author metadata
git blame -e – Instead of displaying the author’s username, the email address is displayed
git blame -m – Identifies lines that have been moved or copied from within the same file. The original author is reported, not the author that relocated that line.
git blame -l – Will display commit hashes at full-length
git blame -t – Displays time and date as a timestamp instead of the default date and time format.

Specifying Ranges with Git Blame

Instead of viewing the Git blame output for every line in a particular commit, you can precisely specify which lines you want to see. To do this, input the range of lines you wish to see along with the filename:

Git blame -L 40,60 <filename>

Git Blame Porcelain Output Format Vs. Default Output

In Git, we use the term “porcelain” to refer to high-level commands that create outputs with specific criteria:

-human-readable -not intended to be parsed -vulnerable to evolutions and changes

Porcelain commands are not stable enough to rely on for scripting purposes. In contrast, the alternative to a porcelain command is a “plumbing” command. Plumbing refers to low-level commands that are more stable and less likely to change.

Additionally, the porcelain format is designed to suppress information you may have already seen. For instance, when viewing two separate lines that are blamed on the same commit, the details for that commit will be shown once instead of twice.

Git blame --porcelain

Git Blame Vs. Git Log

Git blame is ideal when you simply want to see who last modified a line in a particular file, whereas Git log will give you a more general overview of the entire repository.

With Git blame, you can easily see who was the last person to alter a line. However, if you need to take things a step further and figure out how the entire project has evolved over time, you can use the Git log command.

By running a Git log command, you can see a list of all commits made in a repository, along with useful metadata such as the author and date.

Summary

Git blame is a simple, yet valuable command for tracking commit changes that may have multiple authors. Thankfully it’s easy to use and won’t induce any issues or unexpected results with your files. Sometimes you need to identify who introduced a specific bug, which is where the command gets its name. It’s really not meant to be a punitive tool but can help the team provide support to developers or ask questions about what the intention of that line of code was supposed to be.

Next Steps

If you’re interested in learning more about how Git works under the hood, check out our Baby Git Guidebook for Developers, which dives into Git’s code in an accessible way. We wrote it for curious developers to learn how Git works at the code level. To do this we documented the first version of Git’s code and discussed it in detail.

We hope you enjoyed this post! Feel free to shoot me an email at jacob@initialcommit.io with any questions or comments.

Source

LEAVE A REPLY

Please enter your comment!
Please enter your name here