← Back to list

Commit Hygiene That Saves Future You

Part 4 of the “Git & Version Control Mastery” series. “fix”, “fix2”, “asdf”, “final fix” — your git log is a diary of pain nobody can read.

Nazmul Hasan · 2026-06-21 02:01 · 1 claps · 3.3 min read
#github #version-control #best-practices #software-engineering #productivity
Open on Medium ↗
Wiki topics: 🔓 · Open Source ⏱️ · Productivity

Commit Hygiene That Saves Future You

Part 4 of the “Git & Version Control Mastery” series. “fix”, “fix2”, “asdf”, “final fix” — your git log is a diary of pain nobody can read.

Open the history of almost any project and you’ll find it: a wall of commits named fix, wip, 更新, asdf, final, final for real, and the ever-popular .. Each one represents a real change, but the history is useless — nobody can tell what happened, why, or which commit to look at when something breaks. The code works, but the story of the code is gibberish.

Commit hygiene feels like a nicety until the day you’re staring at a six-month-old bug, running git blame, and the only context you get is fix2. Good commits are a gift to your future self and your teammates. Here's how to write them without slowing down.

A commit isn’t a save button. It’s a unit of meaning — a small, complete change with an explanation of why. Treat it that way and your history becomes documentation that’s always up to date.

What a Good Commit Looks Like

Two properties make a commit valuable: it’s atomic (one logical change) and it’s explained (a message that says why).

❌ A bad commit: 600 lines across 14 files, message "updates"
   (Did this add a feature? Fix a bug? Refactor? Who knows.)
✅ Good commits: the same work, split into meaning
   - "Add email validation to signup form"
   - "Fix timezone bug in order timestamps"
   - "Refactor PriceCalculator for readability"

Each good commit is a thing you could describe in one sentence and revert on its own without dragging unrelated changes with it. That’s the whole standard.

Fix #1: One Logical Change Per Commit

The core discipline: don’t mix a bug fix, a feature, and a refactor into one commit. Separate them, because they have different reasons, different risk, and different reasons to be reverted.

  • A reviewer can understand a single-purpose commit at a glance.
  • git bisect (Part 3) can pinpoint a small commit's exact effect; a mixed commit hides the cause.
  • git revert can cleanly undo one change without collateral damage.

When you realize you’ve made several changes before committing, stage them separately:

git add -p          # interactively stage just the chunks for ONE change
git commit -m "Fix timezone bug in order timestamps"
git add -p          # now stage the next logical change
git commit -m "Add CSV export to orders page"

git add -p (patch mode) is the underrated tool here — it lets you commit part of your working changes, so messy "I did three things" work becomes clean, separated commits.

Fix #2: Write Messages That Explain Why

The diff already shows what changed. Your message’s job is the why the diff can’t show. A useful format:

Short summary in imperative mood, ~50 chars
Optional body explaining WHY this change was needed, what
problem it solves, and any context or trade-offs. Wrap at ~72
chars. Reference issues: Fixes #423.

A few rules that make messages instantly better:

  • Imperative mood: “Add caching” not “Added caching” (it reads as “this commit will add caching”, matching Git’s own messages).
  • Summarize the why, not the how: “Fix race condition in payment retry” beats “Change the if statement.”
  • Link context: issue numbers, incident references — the breadcrumbs future-you will follow.

git blame on a line should lead to a commit that explains itself, not one that says fix.

Fix #3: Clean Up Before You Share

Your local work-in-progress can be as messy as you like — wip, wip2, "trying something." The discipline is to tidy it before it becomes public. Interactive rebase lets you reshape local history into clean commits:

git rebase -i HEAD~5     # squash, reorder, reword your last 5 local commits

Squash the five wip commits into one meaningful "Add user notifications" commit, reword unclear messages, drop dead-end experiments. The reviewer sees a clean, logical series — not your stream of consciousness. (Remember Part 1: only rebase local commits you haven't shared.)

Putting It Together

  1. Atomic commits — one logical change each; use git add -p to separate.
  2. Explain why — imperative summary, a body for context, link the issue.
  3. Tidy before sharing — interactive rebase to squash and reword local mess.
  4. Aim for a readable git log — history as documentation, not a diary of panic.

The Takeaway

Commit hygiene is invisible until the moment you desperately need your history to make sense — debugging a regression, reviewing a PR, or running git blame on a line nobody remembers writing. Atomic, well-explained commits turn your Git history into living documentation: every line traceable to a clear reason, every change revertable on its own, every bug huntable with bisect. It costs almost nothing in the moment — separate your changes, write a real message, tidy before you push — and it pays back every single time someone (usually future you) has to understand why the code is the way it is.

This is Part 4 of the Git & Version Control Mastery series. Next up: a branching strategy that doesn’t hurt — choosing how your team uses branches without drowning in process.

What’s the worst commit message you’ve ever written (or inherited)? 👇


메타데이터
post_id
fe7302cfdb2a
slug
commit-hygiene-that-saves-future-you-fe7302cfdb2a
url
https://medium.com/@najmul.hasan284/commit-hygiene-that-saves-future-you-fe7302cfdb2a
canonical_url
https://medium.com/@najmul.hasan284/commit-hygiene-that-saves-future-you-fe7302cfdb2a
author_url
https://medium.com/@najmul.hasan284
status
ok
fetched_at
2026-06-23 03:48:11