As software engineers who use git or other similar version control systems, we tend to write a lot of commits. Is investing in good commits a worthwhile investment?
As engineers, it’s easy to focus on just the code because, after all, that’s what we spend most of our time reading and changing. I’m going to argue that Git isn’t simply a smart diff merger to help us put all code in the same place nor is it just a simple version control system, it can be so much more.
One way I use git commits is to help myself understand what I was doing the day before when writing/changing a lot of code. It gives me a descriptive context that I can read in order to understand what I was doing the day/hours before quicker than just reading the code. This is also useful as a way to share with your colleagues some change you want some feedback on, what better place to write your intentions than in the commit message itself?
If you use git to manage your codebase, then every single line of code is being documented by the commit messages. Along with each change, there’s a git commit message, and if we’re able to document each change with some text describing it in a way that’s not tied to any external services, why not leverage that as a way to document your whole codebase as you write it.
Let’s pretend that you’re working in a codebase where each commit clearly explains the reason why it was added. You are now looking at a piece of code and you want to delete it, but you don’t know if you can. Using
git blame to check the commit itself lets you understand when and why that change happened. You can then know whether you can remove that code (if it’s not needed because it was added as part of an experiment that has finished, for example) or whether you should keep it (it’s really important because the specific version of your DB requires that for example).
Another git tool that can help us with debugging is
git bisect, which helps you find out which commit introduced a bug by helping you check commits using binary search. In this situation, it really helps having atomic commits that have one change only and that are well written so it’s easier for the person debugging to figure out which commit introduced the bug, but also why we made that specific change to answer questions such as: can we revert it?
And speaking of
revert, that’s another good example of how good commits can help you. If each change is isolated in a commit, then it’s easy to
git revert just that specific commit (or some) to fix a problem in production, when speed is crucial.
Let’s split the commit into two parts, the code change and the message.
The code change should be “atomic”, meaning it should not break tests and it should be contained in a particular change.
- Implementing a new API endpoint including tests and documentation
- Implementing a new API endpoint, tests and documentation in three separate commits
- Implementing a change to the code and another commit to “fix tests”
With atomic changes, it’s easier to run
git bisect for finding out problems since you know that every commit keeps the build green, so you won’t have noise with whatever command you’re running to find a particular commit when bisecting and it’s easy to
git revert it for the exact same reason.
As for the message, it should focus on explaining why the change is being added to the codebase rather than what it’s doing since that’s already described in the change itself, this way when you check a commit for a piece of code you’re curious about, you can use it to understand why that code was written and its purpose (when it’s unclear from the code itself).
OK, I managed to convince you and you want to write commit messages that explain the reasoning behind an atomic code change to the code, what can you do next?
- When writing a commit message, ask yourself whether the message explains well the reason for the change to be added to the codebase.
- When making a commit, consider if it can be amended with another commit or if it’s an independent change that doesn’t break the tests.
- Make reviewing merge requests commit by commit a part of the code review process so that you’re only merging good commits into your codebase.
- Share this article with your team and friends (who use git) :)
Because I’m standing on the shoulders of giants, here is a selection of talks/articles that helped me write this article and have helped me improve my own git commits during my career.
- Joel Chippindale | Simplify writing code with deliberate commits talk
- How atomic commits make you a better coder
- Pro git book | "Rewriting history"
- A good talk on git including a story of why git commit messages are useful
- The pro git book is free and a great resource to learn more about git: https://git-scm.com/book/en/v2
- Tom Stuart offers writing git commits as a solution to “Get off the tightrope”