I recently hit a problem where an empty file was renamed differently in two branches but merged without a conflict being raised.
Steps to recreate are as follows.
Create an empty file.
git init
touch empty
git add empty
git commit -m "add empty file"
Rename it in the branch.
git checkout -b branch
git mv empty empty-in-branch
git commit -m "empty -> empty-in-branch"
Rename it differently in the master.
git checkout master
git mv empty empty-in-master
git commit -m "empty -> empty-in-master"
Merge branch into master.
git merge --no-commit branch
This gives the message Automatic merge went well; stopped before committing as requested
.
git status
shows just the new file empty-in-branch
. But there is no deletion of empty-in-master
so if we commit at this stage we'll get both files.
I'd expect this to be flagged as a merge conflict that needed manual resolution (i.e. deciding which empty file to keep). That's what happens if the original file is non-empty.
Is there something special about empty files that affects the rename detection? Are there any parameters I could add to the git merge
that will get it to detect the conflict (e.g. tweaking the merge strategy)?
Empty files are no longer considered for renames on a recursive merge as of this commit: https://github.com/git/git/commit/4f7cb99ada26be5d86402a6e060f3ee16a672f16
Older versions of Git still report it as a conflict.
$ git --version
git version 1.7.9.5
# ... follow OP instructions to reproduce
$ git merge --no-commit branch
CONFLICT (rename/rename): Rename "empty"->"empty-in-master" in branch "HEAD" rename "empty"->"empty-in-branch" in "branch"
Automatic merge failed; fix conflicts and then commit the result.
$ git status
# On branch master
# Unmerged paths:
# (use "git add/rm <file>..." as appropriate to mark resolution)
#
# both deleted: empty
# added by them: empty-in-branch
# added by us: empty-in-master
#
no changes added to commit (use "git add" and/or "git commit -a")
Git doesn't implicitly track renames, so without the rename detection what ends up happening is Git just sees that both commits deleted the file empty
, and that each commit added a new file.
There is an option to change this behavior for git-diff (https://github.com/git/git/commit/90d43b07687fdc51d1f2fc14948df538dc45584b), but currently it is not exposed in an option to git merge
.
The other merge strategies do not seem to give the desired behavior either.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With