macrobug
macrobug

Reputation: 666

How can I find all the merges that had conflicts in a Mercurial repository?

I am working on a research to study merges in open source projects.

I recently asked How can I find all the commits that have multiple parents in a Mercurial repository?, and got a very good answer.

Now I need to narrow my query to only find the commits that had conflicts.

With conflicts I mean that the same file was modified in the two contributing commits.

Also, it would be very useful if I can find a mercurial or bash (grep, awk?) command that gives me only those commits in which the same line was modified by the two contributors.

The idea is to find commits that cannot be auto-resolved.

So, How can I find all the merges that had conflicts in a Mercurial repository?

Upvotes: 0

Views: 164

Answers (4)

Simon King
Simon King

Reputation: 228

For each merge revision, you can retrieve the list of changed files, relative to the first and second parent revisions. Files that appear in both lists are presumably conflicts.

Here's a sample:

for rev in $(hg log -r "merge()" --template '{rev}\n'); do
    hg status --rev "p1($rev)" --rev $rev --no-status | sort > /tmp/p1
    hg status --rev "p2($rev)" --rev $rev --no-status | sort > /tmp/p2
    echo Conflicts in $rev:
    comm -1 -2 /tmp/p1 /tmp/p2
done

Note: this probably won't cope with files being renamed. You could try adding "--copies" to the "hg status" calls.

Upvotes: 1

Lazy Badger
Lazy Badger

Reputation: 97282

  1. Yes, you have to replay each merge between merge-parents
  2. After merge check return-code of merge

Returns 0 on success, 1 if there are unresolved files.

Upvotes: 0

Mark
Mark

Reputation: 462

You can use the filters to isolate all merged files and from that their parents. But you would then need to diff the parents to see if there are any merge conflicts.

Upvotes: 0

Lasse V. Karlsen
Lasse V. Karlsen

Reputation: 391336

There is no simple way to find these as there is nothing recorded in the merge to indicate whether the merge had conflicts or not.

Note that a file that was modified in two branches does not necessarily constitute a conflict, it will only lead to a conflict if the file is:

  1. Unmergeable (ie. binary or similar)
  2. or, at least one area in the file was changed in both branches

If you change the top of the file in one branch, and the bottom in another, and they are sufficiently far away from each other (usually a couple of lines between changes are enough), then this will merge without a conflict.

Your only option is to replay each merge that contains a file that was changed in both branches, making a note of which merges that mercurial cannot merge without conflict.

Also, I don't know of any way to use the built-in query syntax to find merges where the same file was changed in both branches. I think you'll have to go dig in the log yourself (that is, with some code).

Upvotes: 2

Related Questions