2

I'm merging branches. Some commits on the from branch will cause merge conflicts, and others won't. I'd like to know which will cause conflicts*, so I can decide what point to merge to. For example, something like:

# History

F (branch to)   G (branch from)
|               |
D               E
|               |
B               C
 \             /
   -----A-----     

$ git checkout to
$ git find-merge-conflicts from
 C ✓ 
 |
 E ✗ (3 conflicts) 
 |
 G ✗ (1 conflict) 

Does something like this exist?

I looked at git-imerge. It allows me to see this information in a way, as I incrementally merge each commit, but I'm not sure if I can use it to do this query without actually merging.

*By "cause conflicts", I mean running git merge ref will cause conflicted files that need resolution.

Nick Heiner
  • 119,074
  • 188
  • 476
  • 699

1 Answers1

1

Git doesn't let you perform a merge without having a working tree, so if you want to merge two branches, you need to check one of them out and merge the other. There isn't a tool to check just for merge conflicts, and with the state of Git now, it would be a little tricky to add that functionality. If you want to use Git, you can do this:

test_merge () {
    git checkout "$1"
    git merge --no-commit --no-ff "$2"
    local status=$?
    git merge --abort
    return $status
}
test_merge F G

You can run this shell function or a suitable shell script one at a time with the outputs of git rev-list A..G as the second argument.

However, libgit2 does let you perform a merge without checking it out, writing the merge into a temporary index, and either aborting as soon as conflicts are found, or detecting conflicts written into the index. If your language provides a binding to libgit2, you can use that to perform a test merge. Most distributions provide libgit2, so you'd only need to build the bindings for your language.

If you're looking for a command-line tool that operates without checking out the branch, the only one I'm aware of is the one I've written, git test-merge, which, while pretty bare bones, lives at https://github.com/bk2204/scutiger, and is based on libgit2. Others may exist and be more featureful, though, so you should consider searching for other options which may meet your needs better, such as listing the number or names of conflicts.

bk2204
  • 64,793
  • 6
  • 84
  • 100
  • 1
    You can perform a three-way merge with that option if (and only if) you pass all three arguments, but it is a plain three-way merge and not a recursive merge, so it uses a different algorithm and doesn't do renames or other extended features. – bk2204 May 21 '20 at 02:56