You tried to push your changes and git slapped you with this:
This is one of the most common git errors, and it’s actually git protecting you from accidentally overwriting someone else’s work (or your own work from another machine).
Why This Happens
The remote branch has commits that your local branch doesn’t have. This typically occurs when:
- Someone else pushed changes to the same branch
- You pushed from another machine and forgot to pull
- You rebased or amended commits that were already pushed
- A CI/CD pipeline made commits (version bumps, changelog updates)
The Safe Fix: Pull First
In most cases, this is what you want:
| |
The --rebase flag replays your local commits on top of the remote changes, keeping a clean linear history.
If you prefer merge commits:
| |
Handling Conflicts
If the pull results in conflicts, git will pause and let you resolve them:
| |
The Nuclear Option: Force Push
⚠️ Warning: Only do this if you’re absolutely sure you want to overwrite the remote branch.
| |
This is appropriate when:
- You intentionally rebased/squashed commits
- You’re the only one working on the branch
- You need to undo a bad push
Safer Force Push
Use --force-with-lease instead of --force:
| |
This fails if someone else pushed changes since your last fetch, preventing you from accidentally overwriting their work.
Checking What’s Different
Before deciding how to fix it, see what’s actually different:
| |
Common Scenarios
Scenario 1: CI Made a Commit
Your pipeline updated a version file or changelog:
| |
Scenario 2: You Amended a Pushed Commit
You ran git commit --amend on a commit that was already pushed:
| |
Scenario 3: You Rebased a Shared Branch
You rebased main and now can’t push:
| |
Everyone else will need to:
| |
Scenario 4: Diverged History
Your branch and remote have both moved forward:
| |
Prevention
- Always pull before starting work:
git pull --rebase - Push frequently: Don’t let commits pile up locally
- Use feature branches: Avoid pushing directly to main
- Set up pull rebase by default:
| |
Quick Reference
| Situation | Command |
|---|---|
| Safe fix (rebase) | git pull --rebase origin main && git push |
| Safe fix (merge) | git pull origin main && git push |
| Force push (careful!) | git push --force-with-lease origin main |
| See difference | git fetch && git log --oneline --left-right HEAD...origin/main |
The non-fast-forward error is git being helpful, not git being broken. Take a moment to understand what diverged before choosing your fix.