DEV Community

Michael Kohl
Michael Kohl

Posted on • Originally published at citizen428.net on

Git quick tips #1: git commit --fixup

You like clean commit histories. If something goes wrong you use --amend and carry on. Life is good.

The problem

Then it hits you, you forgot something in an older commit. So you have to reach for a heavier gun in the form of git rebase --interactive (or git rebase -i), which offers a handy fixup option:

f, fixup <commit> = like "squash", but discard this commit's log message
Enter fullscreen mode Exit fullscreen mode

Let's see this in action. We are starting from this repository with 3 commits:

$ git log --oneline
4e69593 (HEAD -> trunk) Some more work happened
ea75734 Some work happened
2a030ce First commit
Enter fullscreen mode Exit fullscreen mode

We now notice that we messed up the second commit (ea75734). So we fix the problem and make a new commit:

$ git log --oneline
22c85d6 (HEAD -> trunk) Oops
4e69593 Some more work happened
ea75734 Some work happened
2a030ce First commit
Enter fullscreen mode Exit fullscreen mode

Now we have to rebase the last 3 commits with git rebase -i HEAD~3. This will drop us in an editor and list the commits as follows:

pick ea75734 Some work happened
pick 4e69593 Some more work happened
pick 22c85d6 Oops
Enter fullscreen mode Exit fullscreen mode

We can now reorder them and change "pick" to "fixup" (or "f" for short).

pick ea75734 Some work happened
fixup 22c85d6 Oops
pick 4e69593 Some more work happened
Enter fullscreen mode Exit fullscreen mode

After saving and exiting the editor, our commit history now is clean (notice the changed commit hashes):

$ git log --oneline
321e945 (HEAD -> trunk) Some more work happened
1b33eb6 Some work happened
2a030ce First commit
Enter fullscreen mode Exit fullscreen mode

The solution

While this works, it's a somewhat cumbersome process. But git offers a convenient alternative in the form of git commit --fixup.

Let's go back to our previous example and change the "Some work happened" commit once again, but this time with a fixup commit:

git commit --fixup=1b33eb6
[trunk 3e12b6f] fixup! Some work happened
Enter fullscreen mode Exit fullscreen mode

Not only does this automatically generate a commit message, if we now do the same interactive rebasing operation, the fixup commit will automatically be moved to the right position and have "pick" replaced with "fixup".

pick 1b33eb6 Some work happened
fixup 3e12b6f fixup! Some work happened
pick 321e945 Some more work happened
Enter fullscreen mode Exit fullscreen mode

Discussion (1)

Collapse
albertopdrf profile image
Alberto Pérez de Rada Fiol

I didn't know about this one and used to move and squash the commits manually, thanks for sharing! :)