Fundamentals 13 min read

Master Git Rebase: Clean History, Conflict Resolution, and Safe Force Push

This guide explains what Git rebase is, compares it with merge, shows how to rewrite commit history, handle conflicts, safely force‑push, and recover from mistakes, providing practical commands and tips for developers who work with Git daily.

Code Mala Tang
Code Mala Tang
Code Mala Tang
Master Git Rebase: Clean History, Conflict Resolution, and Safe Force Push

“Don’t force‑push your commits to a remote Git repository!” is common advice, but after extensive Git work the author often uses force‑push successfully.

Many developers fear git rebase because it rewrites history, making recovery difficult if mishandled. This article explains the principles, common use cases, and how to rebase branches like a professional.

What is Git Rebase

Each commit is based on the previous one, so the first commit is the foundation for the second, the second for the third, and so on. Rebase simply changes the base of one or more commits, which sounds easy but can be tricky in practice.

Why not just use merge?

Both strategies are possible, depending on team conventions and needs.

Merge commit:

✍️ Creates a new commit that brings in all commits from another branch.

✅ Preserves commit history.

⚠️ Conflict resolution can be difficult.

❌ History can become cluttered with unnecessary commits.

❌ Makes future rebases harder.

Rebase commit:

✍️ Rewrites history as if the commits were based on a different base.

✅ Produces a cleaner Git history.

⚠️ Conflict resolution can be difficult.

❌ Timeline can become harder to understand.

Modifying History with Rebase

If you have a commit with a bad message several commits back, you can edit it using interactive rebase:

<code>git log --oneline --decorate --color --graph --all</code>

Run git rebase -i HEAD~3 to edit the last three commits. The editor will show:

<code>pick 8b8ded1 Yaahhttzeeeee
pick 2ddd119 good commit 2
pick eb8f720 good commit 3
# ... instructions ...</code>

Common options:

pick : apply the commit as is.

reword : change the commit message.

edit : pause at the commit for any changes.

squash : combine commits into one.

drop : remove the commit entirely.

Change the first line to reword 8b8ded1 Yaahhttzeeeee , save, and edit the message to something like:

<code>good commit 1.5

# Bad name! This is a comment btw.
# Yaahhttzeeeee</code>

After saving, the new history looks like:

<code>git log --oneline --decorate --color --graph --all</code>

Now you can safely force‑push using --force-with-lease instead of plain --force to avoid overwriting remote commits that don’t exist locally.

Remember to always use --force-with-lease rather than --force . It prevents force‑pushing when the remote has commits you don’t have locally.

Updating a Branch with Rebase

After learning to edit commits, you can rebase a feature branch onto main :

<code>git rebase main</code>

The new history will show the feature commits as if they were based on the latest main commit.

Rebase Conflicts Look Scary

Conflicts during rebase are just merge conflicts. When rebasing multiple commits onto main , Git applies each commit sequentially and may pause for conflicts.

<code>Auto-merging README.txt
CONFLICT (content): Merge conflict in README.txt
error: could not apply 0ad2b4f... awesome feature
hint: Resolve all conflicts manually, mark them as resolved with "git add/rm <conflicted_files>", then run "git rebase --continue"
hint: You can instead skip this commit: run "git rebase --skip"
hint: To abort and get back to the state before "git rebase", run "git rebase --abort"</code>

After resolving, add the files and continue with git rebase --continue . Repeat until all commits apply.

What If I Mess Up?

You can abort the rebase at any time with git rebase --abort , which restores the state before the rebase started.

Why Do I Keep Resolving the Same Conflicts?

Git’s git rerere (reuse recorded resolution) automatically re‑applies a previously recorded conflict resolution, avoiding repetitive manual fixes.

Additional Tips

Use git status to check rebase progress.

Create a backup branch before rebasing if unsure.

Advanced shells like zsh or fish display rebase status more clearly.

If you make a mistake, git reflog can help recover lost commits.

gitconflict resolutionrebaseVersion Controlinteractive rebaseforce push
Code Mala Tang
Written by

Code Mala Tang

Read source code together, write articles together, and enjoy spicy hot pot together.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.