27 ms·
How well do various revision tools handle merge conflicts?
- drivebyacct2 14y agoI'd like to see TFS in there. Mostly out of resentment.
- EtienneK 14y agoAgreed. Last week alone I lost code 3 times.
- jcdavis 14y agoSome of the more complicated merges, e.g. "adjacent lines" scare me. The comment says "They clearly don't conflict since they don't modify the same lines." And while that seems obvious for humans reading the given test case, it seems easy enough to construct a situation where that is not the case due to, for instance, a function call spread out over multiple lines. Sadly these merges require a fair amount of language-specific knowledge. That doesn't have to be something that we can't ever expect merge tools to do, but one has to be realistic.
- jbri 14y agoWhat I'd like to see at some point is language-aware merge tools that can both correctly merge stuff like that, and flag conflicting edits even if they don't touch the same source lines.
- qznc 14y agoMore than language-specific knowledge is necessary. Let's say we have two branches to merge: branch A: rename foo() to bar() and adapt calls branch B: add baz(), which calls foo() We can assume that there is no merge conflict here, since A touches various lines within major code blocks and B adds some lines between two code blocks. Now show me one merge tool, which understands that the call to foo() within baz(), must also be renamed to bar(). Most tools will probably just merge and produce a broken build.
- InclinedPlane 14y agoImagine you have a modularized compiler that can round-trip between raw text-based source and parse trees as well as final binaries with associated meta data attached. In that case it's not too far fetched to imagine version control systems that merge at the level of parse trees, which would allow it to detect the conflicts you describe.
- qznc 14y agoDetection is possible. Just automatically try to build it after the merge. Auto-fixing seems impossible to me, though.
- rwmj 14y ago... unless the reason you renamed 'foo' was so you could introduce another function called 'foo' which does foo properly/differently. For a realistic example, suppose you decided that 'foo' should acquire a lock. So you rename all existing 'foo' to 'foo_nolock', and add a new wrapper 'foo' which takes the lock and called 'foo_nolock'. If your other branch called the original 'foo', it should probably now be calling 'foo_nolock', but instead it'll be calling the lock function after the merge, and your compile (or even tests) may not be able to find that error.
- sirclueless 14y agoThis is why the round trip between source-code and parse tree is so great. Say branch A adds a call to foo(), and branch B swaps out foo() for foo_nolock(). You can tell from the round trip on branch A that there was a new reference to foo(). Then in branch B you can tell that the implementation of foo() has changed. I'm not sure how you would represent such a conflict. A valid way to resolve it would be to tell the DVCS, "You dummy, this isn't a conflict, the author of branch B obviously wanted to change foo() for every call-site, even those he didn't know about." The normal diff-file syntax of "this branch added these lines, that branch removed those lines" wouldn't work.
- notaddicted 14y agoFlashback: Discussion of merging 2009: Git: Bram Cohen vs Linus Torvalds http://news.ycombinator.com/item?id=505876 http://news.ycombinator.com/item?id=505876 which refers to 2007: A look back: Bram Cohen vs Linus Torvalds http://www.wincent.com/a/about/wincent/weblog/archives/2007/07/a_look_back_bra.php http://www.wincent.com/a/about/wincent/weblog/archives/2007/... which refers to 2005: Re: Merge with git-pasky II. http://www.gelato.unsw.edu.au/archives/git/0504/2153.html http://www.gelato.unsw.edu.au/archives/git/0504/2153.html Where Linus says: For example, it seems like most SCM people think that merging is about getting the end result of two conflicting patches right. In my opinion, that's the _least_ important part of a merge. Maybe the kernel is very unusual in this, but basically true _conflicts_ are not only rare, but they tend to be things you want a human to look at regardless. The important part of a merge is not how it handles conflicts (which need to be verified by a human anyway if they are at all interesting), but that it should meld the history together right so that you have a new solid base for future merges. In other words, the important part is the _trivial_ part: the naming of the parents, and keeping track of their relationship. Not the clashes. For example, CVS gets this part totally wrong. Sure, it can merge the contents, but it totally ignores the important part, so once you've done a merge, you're pretty much up shit creek wrt any subsequent merges in any other direction. All the other CVS problems pale in comparison. Renames? Just a detail. And it looks like 99% of SCM people seem to think that the solution to that is to be more clever about content merges. Which misses the point entirely. Don't get me wrong: content merges are nice, but they are _gravy_. They are not important. You can do them manually if you have to. What's important is that once you _have_ done them (manually or automatically), the system had better be able to go on, knowing that they've been done.
- natep 14y agoI see that git has been updated to 'pass' the indent-block test, because it produces the correct output, but the resulting indentation is not correct. I have git.mergetool set to bc3 (Beyond Compare 3), so I tried running 'git mergetool' for each of the failed cases. In the adjacent case, bc3 merged things correctly, and all I had to do was accept its merge. In the indent-block case, I just had to fix (some of) the spaces, before accepting the merge. The only case where I had to do some real work was in dual-renames, but even then, it was fairly trivial. So, I agree with you. To me, it doesn't matter that git (or any other tool) sometimes gets content merging wrong. It _is_ gravy, and can be handled by other tools (bc3 in my case). What external tools can't do is manage your history.
- Too 14y agoSee http://www.guiffy.com/SureMergeWP.html http://www.guiffy.com/SureMergeWP.html for another merge test suite with some background material. A year ago i tried a few of them in various diff-tools, none passed all of the tests, including guiffy even though they claim to in the article. Some of the tests can also be considered objective or non-resolvable but it still an eye opener to see how poor the merge tools really are. Btw, i thought merge conflict handling was a feature of the diff tool, not the scm?
- natep 14y agoTry Beyond Compare (I'm not affiliated, just a longtime customer). I just went through each test case and had no problems. Resolving one of the standard conflicts involved using 'align with <F7>' to separate the changes at the end of the file. Most of the pathological cases were solved automatically and without even conflict markers, and when they weren't, selecting a hunk, right clicking, and choosing 'take left then right' worked.
- tomlu 14y agoSeconded. Beyond Compare is the best merge and diff tool bar none.
- lnguyen 14y agoWhen a diff tool is included with the scm, it's hard for the average user to separate the functionality even if it's possible. And odds are you'll probably to be able to use different diff/merge tools to handle various file formats (plain text, xml, binary, etc.) so you won't have to rely on just one getting everything right.
- Too 14y ago*objective -> subjective
- SteveJS 14y agoI thought the three way merge tool was independent of the source control system. I'm pretty sure that's true for the four systems I've used: hg, tfs, perforce, and the horrible horrible SLM. I can say however that SLM's default three way merge just seemed to always do the right thing. Tools for managing real conflicts seem more interesting. Most conflict resolution tools seem to 'help' in a way that leaves me completely baffled. They automate the creation of unintentional edits rather than helping you understand the history of the changes that lead to the conflict, and tracking and reversibility of what you are doing during merge. I've resorted to temporarily overlaying another source control system to track dealing with resolving large complicated merge conflicts.
- sirclueless 14y agoInasmuch as a merge is a 3-way comparison between a common parent and two branches, it is basically DVCS-agnostic. The really interesting thing here is that Darcs doesn't just do three-way merges: it actually tracks every change along the way. From what I understand, Darcs conceptually resolves conflicts as if you rewound one branch and played it on top of the other, and vice versa simultaneously. A conflict is considered resolved if these operations are commutative, that is, the order of commits doesn't affect the result. Manual intervention is required when this fails to be true. This is inherently more powerful than a three-way merge, because you have the entire history of each divergent branch to help you understand changes, instead of only the net effect of each.