This article is part of a series where I make an effort to understand Git deeper instead of just remembering the correct order of git add, git commit and git push. I started last year with two posts on Logs and Diffs and Undoing and/or fixing the last commit. Today I continue by figuring out how to stage only parts of a modified file, specific lines that is. It is not difficult, but you should already be familiar with how files are added to commits through the staging area. If you can do that, you a ready to learn how to only add some changes from a file to the next commit. I think the Git terminology for this feature is called patch.

## A little inception never hurts

The most effective way of learning a Git thing is by applying it (for me at least). Since I have a weak spot for things that reference themselves1 I will apply this Git feature to the code of Git itself. Of course you can use any other Git repository you like (and easily revert changes afterwards).

## Entering patch mode

To get started we need to make changes to some existing file. Here is what I did:

These are some arbitrary changes without meaning but let’s assume I want to add just the comment but not the function. A classic git add would only let me select the file or not, so here is where patch comes in. Add the flag -p or --patch to use it2. This will drop you into an interactive mode where Git asks questions through the prompt. In this case it asks me whether I want to add the comment:

This is exactly what I wanted to be asked, so I say yes by entering y. Git proceeds to the next questions which unsuprisingly is about my second change:

This is a change that (for whatever reason) I don’t want to stage yet. So I say no by typing n. Interactive mode finishes and I am left with the regular terminal prompt. What happened? Let’s see by running git status:

The file I modified is listed twice, once as staged and once as unstaged. This means that some changes are staged but we have additional unstaged changes on top of that version. To see this in detail we can use git diff for both unstaged (default) and staged (--staged) changes:

Here I see that the function is in the unstaged area. My second change, the comment, should therefore be in the staged area. Indeed:

So if I commit now it should only contain the comment but not the function:

I still have one modified file because the function has not been committed. That is basically how patching works. You might have noticed that there are more subcommands than just y and n from the patch prompt. These include some neat shorthands for adding (a) or omitting (q) all changes from the current one to the end of the file. A really helpful one is splitting (s): Sometimes multiple changed lines are shown to you as one piece during the patch process. If they are separated by unchanged lines you can use s to split by them and decide for each part individually.