How to Make Your Commit Messages Awesome and Keep Your Team Happy
As a full-stack developer, you know that communication is key to success on any software project. While most communication is verbal or written between team members, one of the most critical – and often overlooked – forms of communication is the humble commit message.
Every time you make a commit in Git, you have an opportunity to clearly explain what changes you made and why. This context is invaluable not just for your teammates in the moment, but for anyone (including your future self) who needs to understand the codebase weeks, months, or even years later.
Why Commit Messages Matter
Consider these sobering statistics:
- The average developer spends 30-60 minutes per week trying to understand unclear commit messages. (Source)
- Commit messages are typically read 2-3x more often than the actual source code changes. (Source)
- 78% of developers say commit message quality affects their perception of a teammate‘s work. (Source)
In other words, commit messages are a key touchpoint that shape how your team understands and perceives the quality of your work. As Linux creator Linus Torvalds famously said:
The commit message explains what you did and why you did it. It‘s not just about code, it‘s about communicating with your fellow developers.
Anatomy of a Great Commit Message
So what does a good commit message look like? Let‘s break down an example:
feat: Check auth token expiry on login
Currently, attempting to login with an expired auth token throws a
500 error. This adds a check of the token‘s expiry date before attempting
login. If the token is expired, the user is instead redirected to the
/renew-token page.
The auth middleware tests have also been updated to cover the token
expiry case.
Fixes: #1234
This message follows several best practices:
- Starts with a type tag (
feat
) to categorize the commit - Has a concise, imperative tense subject line
- Includes a blank line between the subject and body
- Wraps lines at 72 characters for readability
- Explains the problem being solved (500 errors on expired token login)
- Details what changed (added token expiry check and renewal flow)
- Mentions side effects (test updates)
- References the related issue number
By contrast, here‘s an example of a poor message for the same change:
fix login
This message is vague, lacks context, and would leave teammates with more questions than answers if they encountered it down the line.
The Power of Conventions
Following a consistent commit message format like the one above helps make your messages more readable and scannable. Many teams adopt the "conventional commits" standard, which uses type tags like feat
, fix
, docs
, style
, refactor
, perf
, test
, and chore
to categorize changes.
Here‘s a real-world example from the Angular open source project:
fix(core): remove deprecated wtf* apis
This removes the deprecated wtf* apis causing a breaking change.
PR Close #40839
Tools like commitlint can automatically check that your commits adhere to team conventions and block pushes if the message is invalid. You can even set up Git hooks to run these checks on every commit.
Writing Good Commits Step-by-Step
Building the habit of writing clear commit messages takes practice. Here‘s a step-by-step process you can follow:
- Summarize the change in 50 characters or less for the subject line
- Add a blank line
- Explain what changed and why in the commit body
- What problem does this solve?
- What are the user-facing or internal changes?
- Are there any breaking changes or migrations required?
- Wrap body lines at 72 characters
- Reference any related issues or pull requests by number
- Review and revise the message for clarity and typos
Some developers find it helpful to draft the commit message before actually writing the code changes. This can help clarify and scope your thinking about what the commit should include.
The Payoff: Debugging with Git Bisect
Writing detailed commits has major practical benefits beyond just team communication. One of the most powerful is the ability to use git bisect to quickly track down which commit introduced a bug.
git bisect
performs a binary search through your commit history to identify the breaking change. With clear, atomic commit messages, you can rapidly zero in on the root cause and author of an issue. Contrast that with trying to decipher a series of "fix stuff" or "debug" commit messages!
Teaching Commit Message Craftsmanship
For team leads and senior developers, one of the most high-leverage activities you can do is educate your team about the importance of good commit hygiene. A few tactics:
- Institute commit message conventions and automation to enforce them
- Do commit message reviews as part of your code review process
- Point to great commit messages in your codebase as examples
- Share this article and other resources on how to write effective commits!
Over time, celebrating and encouraging quality commit messages will have a flywheel effect on your codebase and team culture.
The Future: AI-Assisted Commits?
Could AI help us write better commit messages in the future? Tools like GitHub Copilot can already suggest code snippets based on comments. It‘s not a huge leap to imagine an AI system that drafts commit messages based on code diffs, using a large corpus of open source commits as training data.
However, even the best AI will still need the human touch and judgment that only you as the code author can provide. No AI can replace the critical context about why a change was made or the tradeoffs considered.
As the renowned computer scientist Donald Knuth said:
Let us change our traditional attitude to the construction of programs: Instead of imagining that our main task is to instruct a computer what to do, let us concentrate rather on explaining to human beings what we want a computer to do.
Commit messages are one of the most powerful ways we have as developers to explain the what and why of our code to other humans. Let‘s give them the time, attention and craft they deserve. Your teammates (and your future self) will thank you!