Rebase Is ALTER TABLE on Your Commit History
Rebase is where most DBA git tutorials hit a wall. The explanations get abstract. Diagrams appear with arrows pointing in confusing directions. People start arguing about when to use it.
Here’s the DBA translation: rebase rewrites your commit history. It’s ALTER TABLE — changing the structure of something that already exists. Powerful when used correctly. Dangerous when used on something other people are already depending on.

What Rebase Actually Does
When you rebase, you’re taking your commits and replaying them on top of a different starting point. Instead of merging two branches together (which creates a merge commit), rebase makes it look like your work happened after the other changes — in a clean, straight line.
Imagine you created a branch from main on Monday. By Wednesday, your teammates have pushed three new commits to main. You want to incorporate their changes. You have two options:
Merge (what we covered in Post 3): combines the histories, creates a merge commit. Both timelines are preserved.
Rebase: takes your Monday-through-Wednesday commits, lifts them up, moves the base of your branch to the latest main, and replays your commits on top. The result looks like you started your work on Wednesday, after everyone else’s changes.
|
1 2 3 4 5 |
# You're on your feature branch git switch feature/new-index-strategy # Rebase onto the latest main git rebase main |
The Everyday Version: Pull –rebase
The most common use of rebase is one you might already be using without calling it rebase:
|
1 |
git pull --rebase origin main |
This fetches the latest remote changes and replays your local commits on top — instead of creating a merge commit. Most teams prefer this for keeping a clean, linear history.
Think of it as: “Stash my uncommitted work, fast-forward to where the remote is, then replay my changes on top of the new baseline.”
For daily pull operations, git pull --rebase is almost always what you want. It’s the safe, everyday version of rebase.
Interactive Rebase: Restructuring Your Deployment Script
Here’s where rebase gets genuinely powerful — and genuinely DBA-relevant.
You’ve made five commits on a feature branch:
|
1 2 3 4 5 |
a1b2c3d Fix typo in proc name b2c3d4e Add index on OrderDate c3d4e5f Oops, forgot the INCLUDE columns d4e5f6g Add the INCLUDE columns e5f6g7h Update comments |
That history is honest but messy. Before you merge to main, you want to clean it up. Interactive rebase lets you squash, reorder, or edit commits — like restructuring a deployment script before running it.
|
1 |
git rebase -i HEAD~5 |
Git opens an editor showing your last 5 commits:
|
1 2 3 4 5 |
pick a1b2c3d Fix typo in proc name pick b2c3d4e Add index on OrderDate pick c3d4e5f Oops, forgot the INCLUDE columns pick d4e5f6g Add the INCLUDE columns pick e5f6g7h Update comments |
Change it to:
|
1 2 3 4 5 |
pick a1b2c3d Fix typo in proc name pick b2c3d4e Add index on OrderDate squash c3d4e5f Oops, forgot the INCLUDE columns squash d4e5f6g Add the INCLUDE columns squash e5f6g7h Update comments |
Now those five commits become two clean ones: the typo fix, and a single “Add index on OrderDate with INCLUDE columns” commit. Your deployment script is clean.
The Golden Rule: Never Rebase Shared History
This is the one rule you must never break, and the ALTER TABLE analogy makes it obvious why.
Never rebase commits that other people have already pulled.
Rebase rewrites commit SHAs — the unique identifiers. If your teammates have already pulled your original commits, and you rebase (creating new SHAs for the same changes), their history no longer matches yours. The next time they pull, git tries to reconcile two different versions of the same work. It’s a mess.
It’s exactly like running ALTER TABLE on a production table that other processes are actively reading. The structure changes underneath them, and everything breaks.
Safe to rebase: your own local commits that you haven’t pushed yet, or commits on a feature branch that only you are working on.
Never rebase: commits on main, dev, or any shared branch that others have pulled from.
Rebase vs. Merge: When to Use Which
This doesn’t need to be complicated:
Use git pull --rebase for daily syncing with the remote. It keeps your history clean without risk.
Use interactive rebase to clean up your own feature branch before merging it to main. Squash those “fix typo” and “oops forgot” commits into clean, logical units.
Use merge for integrating a feature branch into main or dev. The merge commit serves as a record: “this feature was integrated at this point.”
Use merge whenever you’re unsure. Merge is always safe. Rebase requires more care.
Try This Yourself
|
1 2 3 4 5 6 7 8 9 |
# Make 3 small commits echo "change 1" > file.txt && git add . && git commit -m "First change" echo "change 2" > file.txt && git add . && git commit -m "Second change" echo "change 3" > file.txt && git add . && git commit -m "Third change" # Squash them into one git rebase -i HEAD~3 # Change the second and third lines from "pick" to "squash" # Save and close the editor |
You just consolidated three deployment steps into one clean migration.
The One Sentence to Remember
Rebase rewrites your commit history like ALTER TABLE changes a live schema — powerful for cleanup, dangerous if other people are already depending on the original structure.
Previously: Stash Is Just a Temp Table for Your Changes
Next up: Tags Are Database Snapshots You Can Name