Volume VI · Chapter 8
Conflict Resolution
Merge conflicts, decision conflicts, duplicated work; single-writer claims.2026-07-12 · 9 min read
Three agents spend the afternoon on the same feature branch, each in its own worktree, each with a slice of the work. By evening the team has three problems, all reported the same way in standup: “there’s a conflict.” One is real and mechanical — two branches touched the same lines in a shared config file, and git is refusing to guess which version is right. One is a design problem — one agent added validation with a schema library, another wrote its own hand-rolled checks for what was supposed to be the same input, and neither is wrong, exactly. And one is just waste — two agents built nearly identical retry helpers because nothing told either of them the other had already started.
A team that treats all three as the same problem will over-invest in the one git already handles well and under-invest in the two it can’t see at all. That confusion is the actual subject of this chapter. Isolation and worktrees — covered in the prior chapter — buy agents room to work without stepping on each other in real time. They do nothing to guarantee the work reconciles cleanly, agrees with itself, or wasn’t redundant in the first place. Coordination reduces how often these things happen; it does not make them impossible.
Same word, three different failures
A merge conflict is the narrowest and most familiar of the three. It is mechanically identical to what happens when two humans edit the same file on different branches: git tracks the common ancestor, both sides’ changes, and when the same region was touched by both, it declines to pick a winner and asks a person — or, increasingly, an agent reading the diff — to resolve it. Nothing about this is specific to AI-generated code. What is different is the rate at which it can be produced: an agent can generate a large, fast diff across many files in the time it takes a human to open one, without the informal social coordination — “I’m touching the config today, are you?” — that keeps human teammates out of each other’s way by default.
A decision conflict is a different animal, and git cannot see it at all. It happens when two agents, working on what is supposed to be the same problem, independently reach incompatible design decisions — one picks a validation library, the other writes bespoke checks; one normalizes dates to UTC at the boundary, the other assumes local time throughout. Nothing about either choice needs to be wrong on its own. The conflict exists before a single line is merged, sometimes before either agent has written code at all, and it can survive a clean merge undetected — both branches compile, both pass their own tests, and the codebase is left internally inconsistent about a decision it never actually made once.
Duplicated work is not a conflict in the technical sense at all — it is a coordination failure that happens to look like one from a distance. Two agents did the same task because neither one knew the other had claimed it. There is no git conflict, because there may be no shared file; there is no decision to arbitrate, because both agents may have made the same reasonable choice. There is only cost: two sessions’ worth of tokens and time spent solving a problem that needed solving once. This is the failure mode the previous chapter’s shared task list exists to prevent, and it is the cleanest of the three to fix — because, unlike the other two, it can be stopped before either agent starts typing.
What the data actually shows
The clearest quantified evidence concerns the mechanical kind. A 2026 study built a dataset of over 142,000 pull requests opened by AI coding agents across roughly 59,000 GitHub repositories, successfully simulated merges for more than 107,000 of them, and found a 27.7% conflict rate — with conflict frequency varying by which agent generated the branch. That figure describes what shows up as a git conflict after the fact; it says nothing about decision conflicts or duplicated work, which by definition leave no trace in a merge simulation, because they either merge cleanly (decision conflicts) or never collide on a file at all (duplication). A single recent paper is evidence, not consensus — the number should be read as an order of magnitude for one dataset, not a universal rate.
The duplicated-work failure has a more anecdotal but concrete account. Anthropic’s writeup on its multi-agent research system describes exactly this pattern in production: “one subagent explored the 2021 automotive chip crisis while 2 others duplicated work investigating current 2025 supply chains, without an effective division of labor.” Their fix was not a smarter agent — it was a more disciplined lead agent, one that gives each subagent “an objective, an output format, guidance on the tools and sources to use, and clear task boundaries” before any work starts. That is a specification problem, and the previous chapter’s shared task list is the mechanism; this chapter is about what happens when the specification still leaves room for two agents to disagree, or two divided tasks still touch the same code.
Three kinds of conflict, side by side
| Conflict type | What actually happened | Where it becomes visible | What resolves it |
|---|---|---|---|
| Merge conflict | Two branches edited the same lines; git can’t determine which change to keep | git status, a failed merge, a PR check | Manual resolution, a mergetool, or an agent reading both sides’ intent |
| Decision conflict | Two agents made different, incompatible design choices for the same problem | Code review — or never, if only one branch is ever merged | A human, a designated lead agent, or a judge (Chapter 9) |
| Duplicated work | Two agents did the same task because neither knew the other had claimed it | Wasted spend, near-identical implementations, nothing to “merge” at all | Prevented, not resolved — a shared task list and a claim, before work starts |
Single-writer claims: settling it before anyone starts
The strongest available prevention for duplicated work — and for the subset of decision conflicts that are really just “who owns this” questions — is making task ownership atomic. The mechanism is old and well understood outside AI coding: an atomic compare-and-swap, the operation Maurice Herlihy showed in 1991 to be powerful enough on its own to implement essentially any concurrent data structure, updates a value only if it still matches an expected prior value, and fails cleanly — not destructively — if it does not. Applied to a task queue, the pattern is a conditional update: claim this task only if its status is still “unclaimed,” and if two agents race for it, exactly one update matches and the other returns nothing to act on. Nobody has to detect the race after the fact, because it was never possible for both to win.
This is also, separately, a well-established design principle for avoiding contention generally: the single-writer principle, articulated by Martin Thompson in the context of high-throughput systems, holds that any given piece of mutable state should be owned by exactly one execution context for all its writes. Applied to a team of agents, that execution context is a session, and the piece of state is a task. One recent practitioner account of orchestrating parallel coding agents states the same rule in plainer terms: “one file, one owner — never let two agents edit the same file.” The rule is older than AI coding and will outlive the current generation of agents; what changes is only how cheaply it can now be violated at scale if nobody enforces it.
What claiming does not fix
A clean claim settles who is doing the work. It does not guarantee the work stays isolated, or that two cleanly divided tasks made compatible assumptions about each other. A practitioner guide to running multi-agent coding workspaces names this precisely: real repositories have “collision hotspots” — routing tables, configuration files, shared component registries — that many unrelated features touch, so even two agents that never disputed who owned which task can still land a git-level merge conflict on the file that both of their tasks happened to pass through. And a decision conflict can appear inside a single, well-claimed task’s boundary if that task’s scope was ambiguous about what the earlier task it depends on had already decided — the claim settles ownership, not agreement.
So the honest claim for this chapter is narrower than “claiming prevents conflict.” Claiming prevents one specific failure — starting the same work twice — completely, by construction, because the second attempt has nothing to act on. It reduces some decision conflicts, the ones that were really ownership disputes wearing a design disagreement’s clothes. It does not touch merge conflicts caused by shared files, and it does not touch decision conflicts between two agents who were never disputing ownership at all, just reaching different conclusions about the same open question. Those need a resolution step, not a prevention step — which is where the second half of this chapter’s honesty has to sit.
When it happens anyway
For a mechanical merge conflict, resolution is well trodden: git presents both sides against their common ancestor, a person or an agent reads the surrounding history and code to understand what each side was trying to do — not just what changed, but why — and picks, blends, or asks. This is the one row in the table where “resolve it after the fact” is a perfectly reasonable default, because git’s own machinery already does most of the work of surfacing exactly where the disagreement is.
A decision conflict needs a different kind of resolver, because there is no diff to read — there is a disagreement about what should have been decided once. Three shapes of answer show up in practice, and they are not mutually exclusive: a human arbitrates, which is reliable and does not scale past a handful of concurrent conflicts a day; a designated lead agent has standing authority to break ties within its delegated scope, which scales further but concentrates the same failure modes a human lead would have; or a judge evaluates the finished alternatives against evidence — cost, test results, static quality signals — rather than trying to referee the disagreement in the abstract. That third shape is the subject of the next chapter, and it points at a genuinely different strategy: instead of trying to prevent two agents from diverging, let them diverge on purpose, in isolation, and pick the better result once both exist.
What to check on Monday
- Give every claimable unit of agent work a real claim — a conditional write a second attempt can lose cleanly — not a Slack message or a shared doc nobody re-reads mid-session.
- Stop treating merge conflicts as a crisis. They are the one failure mode in this chapter git already surfaces and tooling already resolves; spend review time on the other two instead.
- Decide who breaks ties on decision conflicts before agents start working, not after two branches disagree. “We’ll figure it out in review” is a decision to let review be the arbiter — say so on purpose.
- When two claimed, cleanly divided tasks still collide on the same file, treat it as a task-boundary bug in the decomposition, not an agent bug — the fix is a better split, not a stricter merge policy.
- If duplicated work keeps happening despite claims, the claim mechanism probably isn’t reaching every place work gets started — check for a side channel, like a human kicking off a session by hand, that bypasses the shared task list entirely.
For Discussion
- The next time two agents’ branches conflict at the git level, can your team tell within the hour whether it’s a genuine merge conflict, or a decision conflict that happened to land on the same file?
- Who currently has the authority to break a tie when two agents made different, individually defensible design choices for the same problem — and was that decided before the agents started, or only after they disagreed?
- If you instrumented how often two sessions solve the same problem independently, would that number look like an agent failure, or a gap in what your task list actually tracks?
References
- establishedAdvanced Merging — how git represents and resolves a merge conflictPro Git, 2nd Edition (git-scm.com) · 2014-12-24
- emergingAgenticFlict: 27.7% conflict rate across 107,000+ simulated merges from 142,000+ AI-agent pull requestsOgenrwot & Businge, arXiv (AIware ’26) · 2026-04
- establishedDuplicated subagent work without task boundaries; fix via explicit objective, output format, and scope per subagentAnthropic engineering — multi-agent research system · 2025-06-13
- establishedWait-Free Synchronization — compare-and-swap as a universal atomic primitiveMaurice Herlihy, ACM Transactions on Programming Languages and Systems · 1991-01
- establishedThe Single Writer Principle — mutable state owned by exactly one execution contextMartin Thompson, Mechanical Sympathy · 2011-09
- emergingCollision hotspots (routing tables, configs, registries) cause merge conflicts even with cleanly divided tasksAugment Code — how to run a multi-agent coding workspace · 2026-06-18
- emerging“One file, one owner” — never letting two agents edit the same fileAddy Osmani — The Code Agent Orchestra · 2026-03-26