How to Resolve a Git Merge Conflict Without Guessing
When a merge pauses, markers show competing versions, not which to keep. Learn to inspect both sides, write the intended result and review before continuing.
If git merge ends with “Automatic merge failed; fix conflicts and then commit the result,” the repository is paused, not ruined. Run git status to see every unmerged path. Then inspect both versions, write the result the project needs, stage only the resolved files and review what Git will commit. Git records that you staged a choice; it cannot tell you whether the choice is correct. The Git 2.50.0 merge manual documents this workflow.
This guide covers an ordinary command-line git merge. If git status says a rebase is in progress, use that operation’s continuation command instead: Git’s rebase manual says to resolve and stage the file, then run git rebase --continue. During a rebase, the labels ours and theirs can mean the opposite of what you expect in a normal merge.
1. List every unmerged file
From the repository, run:
git status Look for the *Unmerged paths* section and note each file. In short status output, UU means both sides modified a path; other codes can indicate an added or deleted file. The Git status manual lists these conflict states. Some conflicts have no useful text markers, so use the status list as your complete checklist.
Before future merges, commit or stash work you need to keep. If you choose to cancel a merge already in progress, git merge --abort tries to restore the pre-merge state, but Git warns it may not reconstruct local changes that were present when the merge began. That is why the merge manual recommends getting your work in good shape first.
2. Read the competing versions in context
Open a text conflict in your editor. A standard conflict block looks like this:
<<<<<<< HEAD
api_timeout = 15
=======
api_timeout = 30
>>>>>>> increase-timeout For an ordinary merge, the section after <<<<<<< HEAD is from the branch you had checked out. The section after ======= is from the branch being merged. The closing marker names that other side. These markers frame the disputed region; they do not say which side is newer or correct.
Decide what the final file should contain. For a single-valued setting such as api_timeout, choose the value that matches the project’s requirements. If the changes are independent, a valid resolution might combine them, but only when the file format and the application support that result. Do not keep both versions just to make the markers disappear.
If you need the original context, Git keeps the three versions for a normal merge conflict in the index. When those stages exist, inspect them with:
git show :1:path/to/file
git show :2:path/to/file
git show :3:path/to/file Stage 1 is the common ancestor, stage 2 is the checked-out HEAD, and stage 3 is the branch being merged (MERGE_HEAD). This is useful when a long edit obscures what changed on each side; the merge manual documents these stage numbers.
Edit the working file into its intended final form and remove the conflict-marker lines. Search the file for any remaining <<<<<<<, ======= and >>>>>>> markers, then inspect each result in context; a project might also contain those characters as literal text.
When there are no text markers
A delete-versus-edit conflict or a binary file may not give you a useful text block. Check the conflict type in git status and decide whether the final repository should contain the file. If it should, restore or create the intended version and stage it. If it should be absent, remove it from the merge with git rm -- path/to/file. The Git 2.50.0 `git-rm` manual documents that command.
3. Stage only the files you resolved
After editing one file, mark that path resolved:
git add -- path/to/file The -- separates Git options from the filename. Repeat this for each resolved path from git status. Staging a file tells Git to use its current contents in the merge result; it does not test the code or check that your decision matches the issue.
4. Review the result, then continue
Check the merge state and inspect the staged file:
git status
git diff --cached -- path/to/file
git diff --cached --check git diff --cached shows what is staged for the next commit relative to HEAD; the Git 2.49.0 diff manual describes that comparison. git diff --cached --check checks the staged changes for leftover conflict markers and whitespace errors. It is an extra safeguard, not a behavior test. Review the full staged diff and run the project’s relevant tests if the conflict changed code or configuration.
When every conflict is staged, git status should report that all conflicts are fixed while the merge is still in progress. Finish that merge with:
git merge --continue If Git still lists an unmerged path, return to that file and resolve or stage it. If the result is uncertain, pause and inspect the base and both sides or ask a maintainer before continuing.
The useful finish line is not simply a file with no angle-bracket markers. It is a reviewed final version for every conflicted path, staged changes you intended, and project checks appropriate to the change.