Interactive Rebase for Clean Commit History
Summary: Use git rebase -i
to squash, edit, or reorder commits.
A clean and well-structured git commit history is the hallmark of a professional development workflow. When collaborating with others, a logically ordered and easily readable commit log helps everyone understand what changes were made, and why. One of the most powerful tools Git offers for crafting such a history is interactive rebase, accessed via git rebase -i
.
Whether you're squashing "fix typo" commits, reordering changes to make review easier, or editing a message that needs more detail, interactive rebase is your go-to solution. This post will guide you through its uses, best practices, and common pitfalls.
What is Interactive Rebase?
Interactive rebase is a command that lets you rewrite a series of commits. It opens your text editor with a list of recent commits, allowing you to:
- Squash (combine) commits into a single one
- Edit commit messages or the content of commits
- Reorder the order of commits
- Drop commits entirely
The basic syntax is:
git rebase -i <base_commit>
Here, <base_commit>
is the commit before the first one you want to change.
Why Clean Up Your Commit History?
Before we dive in, let's understand why you'd want to do this:
- Easier code review: Well-defined commits help reviewers understand and isolate changes.
- Bisecting made easy: Smaller, functional commits help with bug tracking using
git bisect
. - Project documentation: Commit history doubles as a timeline of development decisions.
- Collaboration: Clean history is less intimidating for teammates, maintainers, and open-source contributors.
How to Use Interactive Rebase
Suppose your repository has the following commit history:
a1b2c3d Fix bug in parser
d4e5f6g Address review comments
e7f8g9h Implement parser feature
And you want to squash "Address review comments" into "Implement parser feature" for a cleaner history. Here's how:
Step 1: Start the Interactive Rebase
Find the commit before those you want to change:
git log --oneline
Suppose abc1234
is the commit before "Implement parser feature".
Start the rebase:
git rebase -i abc1234
Step 2: Edit the Todo List
Your editor will open with something like:
pick e7f8g9h Implement parser feature
pick d4e5f6g Address review comments
pick a1b2c3d Fix bug in parser
Change pick
to squash
(or s
) for "Address review comments":
pick e7f8g9h Implement parser feature
squash d4e5f6g Address review comments
pick a1b2c3d Fix bug in parser
Step 3: Reword Commit Message (Optional)
After saving and closing the editor, Git will prompt you to edit the commit message for the squashed commits. Adjust as needed, save, and close.
Step 4: Complete the Rebase
If there are no conflicts, the rebase will finish automatically. If conflicts occur, Git will pause so you can resolve them. After fixing, run:
git add <file>
git rebase --continue
Reordering or Dropping Commits
- To reorder, just rearrange the lines in the editor.
- To drop a commit, delete its line.
Editing a Commit’s Content
To modify a previous commit (let’s say to include a missing file):
- Change
pick <commit>
toedit <commit>
in the todo list. - When Git stops, make your changes and stage them.
- Run
git commit --amend
. - Continue the rebase with
git rebase --continue
.
Best Practices
- Avoid rewriting public history! Never rebase commits that others have used as a base (except by agreement).
- Rebase before merging: Clean up your feature branch before making a pull request.
- Keep your rebase focused: Limit rebases to your feature branches, not the whole repo.
Common Pitfalls
- Merge Conflicts: Rebasing can trigger conflicts. Take time to resolve them carefully.
- Lost Commits: If you accidentally drop or squash away necessary changes, use
git reflog
to recover. - Force Pushing: After rewriting history, force push (
git push --force-with-lease
) to update your remote branch.
Conclusion
Interactive rebase provides a powerful way to curate your commit history, making your repository easier to understand, review, and maintain. Whether you're preparing to merge a feature branch or just tidying up your work, mastering git rebase -i
is an essential skill for every developer.
Further Reading:
Ready to give your commit history a makeover? Fire up your editor and try git rebase -i
today!