All Articles

Git's interactive patch mode

Some of Git’s index-related subcommands, like git add, support the ‑‑patch (or ‑p) flag that allow you to selectively modify your index. You may already know this, but not use it; you’ll find out it’s not only useful, but that it will help you prevent mistakes, improve the quality of your code and its history, and increase productivity! How’s that for marketing?

Create logical commits

For example, git add ‑p helps me create logical commits when my working tree contains unrelated changes by staging only a subset of changes called hunks.

Me staging a deletion like a boss
Me staging a deletion like a boss. Look at that hunk. Damn.

Until maybe two years ago, I remember I would undo and reapply changes in my working tree so I could commit smaller change sets. Using the patch flag, I am much more efficient.

Having these smaller commits allow me to write more relevant commit messages, enabling me to convey to other developers (including my future self) what the intent of the commit is.

Improve the quality of your code

The patch flag not only allows me to be more productive, I’ve found that it can also lead to improved code quality.

By using git add ‑p, I am forced to go over my changes one by one, through which I often find little mistakes to fix, which I would normally have committed and found out about later. At the same time, I can spot opportunities for improvements. This has notably improved the quality of the code I deliver.

Other subcommands

git add is only one of five Git subcommands that supports the patch interface. For your reference, the following subcommands support the ‑‑patch flag:

  • git add ‑p — Selectively stage changes
  • git commit ‑p — Selectively stage changes and commit immediately
  • git reset ‑p — Selectively remove changes from your index
  • git checkout ‑p — Selectively undo changes in your working tree, reverting them to the state in HEAD
  • git stash ‑p — Selectively stash changes

Demo

The patch interface supports many commands, but I’ve listed and explained the most important ones below:

  • y — stage this hunk
  • n — do not stage this hunk
  • q — quit; do not stage this hunk or any of the remaining ones
  • s — split the current hunk into smaller hunks
  • ? — print help

The following demo shows how git checkout ‑p and git add ‑p can be used to to discard changes and stage two hunks into separate commits.

asciicast

Reading material


Bleep, blorp, black holes.
Reinier Kip on Twitter