Last Updated: December 31, 2020
·
41.41K
· bsimpson

git rebase --autosquash

Scenario

When working in a feature branch, I make some changes to a file and then commit these changes. Later on, I make some additional changes to the same file on the same lines, and I want to squash these changes into the first commit touching the file.

Git rebase

You can do an rebase --interactive (or git rebase -i for short), and change the commit line from a pick to a fixup and place the commit beneath the commit to be squashed into.

This cleans up your commits, but it can be tedious if you have more than just a few commits you want to squash. That is where --autosquash comes into the picture.

From the man git-rebase page:

--autosquash
When the commit log message begins with "squash! ..." (or "fixup! ..."), and there is a commit whose title begins with the same ..., automatically modify the todo list of rebase -i so that the commit marked for squashing comes right after the commit to be modified, and change the action of the moved commit from pick to squash (or fixup).

So by prefixing the commit message with either fixup! or squash! followed by the wording of the commit message to be squashed into, an interactive rebase will setup the todo list for you automatically.

Example

Say I have three commits (git log), and I want commit 5929914 to be squashed into commit 13e88b0:

commit 5929914169c97c08e9da967ba5f6d49704aaa999
    More changes to Fix query for finding rows

commit 11c85ef5b907541b1b5f8fa7ef72e5d2c4f7b55c
    Add unique constraint for calendar audiences

commit 13e88b0f2ec738b7ae61cc91a80067f0aed91c32
    Fix query for finding rows

When I issue git rebase HEAD~3 -i I see the following list:

pick 13e88b0 Fix query for finding rows
pick 11c85ef Add unique constraint for calendar audiences
pick 5929914 More changes to Fix query for finding rows

If I reword my commit message per the documentation for --autosquash to be the following, commit 5929914 should be automatically positioned under commit 13e88b0 with the action changed to fixup:

commit 5929914169c97c08e9da967ba5f6d49704aaa999
    fixup! Fix query for finding rows

commit 11c85ef5b907541b1b5f8fa7ef72e5d2c4f7b55c
    Add unique constraint for calendar audiences

commit 13e88b0f2ec738b7ae61cc91a80067f0aed91c32
    Fix query for finding rows

Now with the command: git rebase HEAD~3 -i --autosquash I get the following automatically changed in my todo list:

pick 13e88b0 Fix query for finding rows
fixup 5929914 fixup! Fix query for finding rows
pick 11c85ef Add unique constraint for calendar audiences

Voila! Now stop wasting your time moving around fixup and squashes

4 Responses
Add your response

Note that you can use the commit SHA of the target commit as the message as well

over 1 year ago ·

@bsimpson: I think you should add that note somewhere in the article, not many people are going to see that in the comments ;)

over 1 year ago ·

Using the commit title is recommended. The reason is interesting and subtle. I have had reason to do multiple passes using git rebase --interactive --autosquash. Sometimes, it is necessary to avoid to many conflicts if you can rebase in multiple passes. Using the title allows the commit number to change without loosing the reference to the commit.

over 1 year ago ·

Thanks for this! I've been using git commit --fixup without knowing about the rebase option.

Note that you could turn this on by default for all rebases, by:

$ git config --global rebase.autosquash true

over 1 year ago ·