TIL about the concept of slots that Git uses for merges
According to an answer on this question: https://stackoverflow.com/questions/50232177/tell-git-to-resolve-conflict-with-a-third-file-which-is-the-answer and to the best of my understanding of that answer, git may use up to four slots in its index (staging area, cache) for a file.
If there is no merge problem, the file you've changed is simply in slot 0 and that's it. If there is a merge problem however:
- Your version of the file ("ours") is in slot 2,
- The version it is in conflict with ("theirs") is in slot 3
- The most recent common ancestor is in slot 1
Your job is then to resolve the conflict within the file in your working tree which now has conflict markers based on these files, and place the resolved version in slot 0, and then git can commit it as per usual.
According to another answer by the same author (torek),
you can get to the contents of a file in a slot like this:
git show :3:path/to/filename
…and then you can store that somewhere. This means that you can save away a conflicting version under a new name, which ought to be good for when you need some kind of conflict resolution when no human is around (or at least no git-human around).
git show :3:path/to/filename > path/to/new-filename
Actually easier is probably to save away the local commit under a new name, and then just remove the original filename
git show :3:path/to/filename > path/to/new-filename
And then git add that and some git reset on path/to/filename.
Automatically create a diverging file instead of merging two versions
Here is a way that could work for that:
Do a git merge
git merge their-branch
If that does not go cleanly, save away the incoming conflicting file with
git show :3:path/to/filename > path/to/new-filename
Then do a
git merge --abort
Then do a git merge again buth with strategy ours:
git merge their-branch -s ours'
Actually, a better method may be to specify a custom mergetool
git mergetool -t /path/to/custom/mergetool
Then that tool can whatever it wants.
According to git docs:
the configured command line will be invoked with
$BASE
set to the name of a temporary file containing the common base for the merge, if available;$LOCAL
set to the name of a temporary file containing the contents of the file on the current branch;$REMOTE
set to the name of a temporary file containing the contents of the file to be merged, and$MERGED
set to the name of the file to which the merge tool should write the result of the merge resolution.