September 1, 2026 · Harness Engineering · Coding Agents · Git · EN

How to Resolve Merge Conflicts Between Coding Agents

A contract-first workflow for resolving textual, semantic, generated-output, migration, and authority conflicts between Claude Code, Codex, Cursor, and other coding agents.

How to Resolve Merge Conflicts Between Coding Agents

How to Resolve Merge Conflicts Between Coding Agents

Resolving a merge conflict between coding agents means reconstructing the intent and authority behind both branches, choosing the accepted contract, and proving the combined behavior—not merely deleting Git conflict markers.

Claude Code can change an API while Codex updates a client. Cursor can edit the same component while another agent changes its design-system contract. Git may report a conflict, but the markers are only the visible symptom. The real disagreement may be about ownership, behavior, generated output, migration order, or which instruction was authoritative.

A reliable conflict-resolution workflow answers five questions:

  1. What outcome did each branch intend to produce?
  2. Which exact base and assumptions did each agent use?
  3. What kind of conflict occurred?
  4. Which repository source has authority over the disputed behavior?
  5. What executable evidence proves the resolution?

This guide focuses on that repair loop. For the broader sequence around it, start with How to Integrate Changes from Multiple Coding Agents and Git Worktrees for Multiple Coding Agents.

Why conflict markers are not the conflict

Git compares text. Your system depends on contracts.

Two branches can edit the same lines for unrelated reasons, producing a noisy textual conflict that is easy to resolve. More dangerously, they can edit different files while implementing incompatible assumptions:

agent/api
  changes: openapi/avatar.yaml
  new behavior: 422 response with field_errors[]

agent/web
  changes: src/avatar/upload.ts
  assumed behavior: 400 response with message

Git result: clean merge
Runtime result: broken error handling

The merge is textually clean and semantically wrong.

Treat every agent branch as a bundle of claims:

Branch claimConflict review asks
intended outcomeDo both branches still serve the same user-visible goal?
exact baseDid either branch start from stale repository state?
changed contractsWhich branch produces the accepted schema or behavior?
implementationAre the edits compatible with that contract?
evidenceWhich checks passed, and what did they actually prove?
omissionsWhich shared boundaries were never tested?
authorityWhich file, decision, or owner decides the disagreement?

Conflict resolution starts by reconstructing these claims before editing the candidate.

The contract-first conflict loop

Contract-first coding-agent conflict-resolution loop Two frozen agent checkpoints enter an intent reconstruction gate. The integrator classifies the conflict, resolves the authoritative source, regenerates derived output, and validates the combined candidate. A failed gate returns to the last known-good checkpoint and the owning source branch. FREEZE → RECONSTRUCT → CLASSIFY → RESOLVE SOURCE → PROVE CHECKPOINTS commits · bases evidence · risks INTENT GATE outcomes reconstructed authority identified CLASSIFY text · contract · behavior generated · migration · authority SOURCE REPAIR accept contract adapt · regenerate COMBINED PROOF boundary checks user-visible outcome PROOF FAILED preserve evidence · restore checkpoint · repair owning source Durable prevention moves into ownership maps, task envelopes, generators, validation scripts, or repository instructions.

The loop deliberately returns to a source branch or canonical controller. Fixing only the integration branch leaves the original checkpoint and its handoff wrong, so the next integration repeats the same failure.

1. Freeze both sides before editing

Do not resolve a conflict while one agent is still writing. Freeze each branch at a stable commit and record its base.

git fetch origin
git rev-parse agent/api
git rev-parse agent/web
git merge-base agent/api origin/main
git merge-base agent/web origin/main
git diff --check origin/main...agent/api
git diff --check origin/main...agent/web
git status --short

For each side, capture:

## Conflict input
- Task: avatar API errors
- Branch: `agent/api`
- Commit: `4d31...`
- Base: `origin/main@a13f...`
- Outcome: return field-level validation errors
- Produces: OpenAPI response schema and server behavior
- Evidence: API contract suite — PASS, 18 tests
- Not run: generated clients and browser flow
- Residual risk: consumers may still expect the old error shape

If a tree is dirty, ask the agent to create a coherent checkpoint or explicitly name the uncommitted paths. An active workspace is not a reproducible conflict input.

2. Reconstruct intent before choosing lines

Conflict tools present versions of files. They do not present the reason each version exists.

Before resolving, the integrator should be able to state:

  • the user-visible outcome of each branch;
  • the exact contract each branch produces or consumes;
  • the repository instruction or decision each agent followed;
  • whether either branch used a stale base;
  • the tests that passed and the surfaces they did not cover;
  • the owner or canonical source for the disputed behavior.

A compact reconstruction table helps:

QuestionAPI branchWeb branch
outcomestructured validation errorsrender upload errors inline
producesOpenAPI schema + server behaviorUI behavior
consumesproduct decision 0042TypeScript client + public errors
basea13f...a13f...
proofAPI contract testscomponent tests with fixture
gapno generated-client checkfixture is hand-authored
authorityopenapi/avatar.yamlconsumes API authority

The resolution is now clear: accept the authoritative API contract, regenerate the client, and adapt the UI. Choosing “ours” or “theirs” by line count would hide the dependency.

3. Classify the conflict

Different conflict classes require different repairs. Use at least these six.

Textual conflict

Both branches changed overlapping lines but may still agree on behavior.

Repair: reconstruct both intents, produce one coherent implementation, and rerun checks covering the affected code. Do not assume a small conflict is low-risk; one changed condition can alter behavior.

Contract conflict

Branches disagree about a schema, public function, CLI, event, configuration key, persisted format, or error shape.

Repair: identify the contract owner and canonical source, accept one explicit version, adapt every consumer, and run compatibility checks. Do not average two contracts into an undocumented third option.

Generated-output conflict

Generated files differ because branches used different schema revisions, templates, lockfiles, or generator versions.

Repair: resolve the source inputs and tool version, discard conflicting derived output, regenerate, and verify the generated tree is clean on a second run.

Behavior conflict

Files merge without markers but the combined runtime behavior is wrong. Middleware order, fallback precedence, shared state, or error handling may interact.

Repair: add a failing boundary or outcome test, decide the accepted behavior, repair the owning implementation, and keep the test as durable evidence.

Migration conflict

Branches introduce database, configuration, or persisted-state transitions that are individually valid but unsafe in combination or order.

Repair: define forward order, compatibility window, retry behavior, and rollback. Test from realistic old state through the combined migration and back where rollback is supported.

Authority conflict

Agents followed contradictory instructions, decisions, or ownership claims.

Repair: stop editing code. Resolve the canonical instruction or decision first, then replay the affected work against one authority. Code cannot decide which governance source should have won.

Use a resolution matrix:

Conflict classFirst authority to inspectRequired proof
textualbehavior owner + nearby testsfocused tests and diff review
contractschema/spec/API ownerproducer-consumer compatibility
generated outputsource schema/template + pinned tooldeterministic regeneration
behaviorproduct invariant + runtime ownerreproducer and outcome test
migrationpersisted format + migration journalforward, retry, and rollback proof
authoritycanonical instructions/decision recordclean-session reconstruction

Classification prevents the conflict editor from becoming the decision system.

4. Create a disposable integration candidate

Resolve conflicts on a dedicated candidate from an exact clean base. Keep worker branches intact.

git switch -c integration/avatar-errors origin/main
git rev-parse HEAD

git merge --no-commit --no-ff agent/api
# Resolve and validate the producer boundary before continuing.

Record the plan before editing:

## Conflict-resolution plan
- Base: `origin/main@a13f...`
- Candidate: `integration/avatar-errors`
- Inputs: `agent/api@4d31...`, `agent/web@73af...`
- Accepted authority: `openapi/avatar.yaml`
- Conflict owner: integration lead
- Contract owner: API maintainer
- Gate 1: API contract suite
- Gate 2: regenerate client twice; second run clean
- Gate 3: web typecheck and component tests
- Final gate: browser upload-error smoke flow
- Rollback checkpoint: clean base `a13f...`

A dedicated candidate makes failed experiments cheap. It also prevents conflict edits from leaking into main or into a worker branch whose original claim must remain inspectable.

5. Resolve the authoritative source first

The safest order is:

  1. decide the accepted behavior;
  2. resolve its canonical source;
  3. update or regenerate derived artifacts;
  4. adapt downstream consumers;
  5. validate each dependency boundary;
  6. prove the combined outcome.

For the avatar example:

# After accepting the final OpenAPI contract:
scripts/validate-api avatar
scripts/generate-clients
scripts/check-generated-clean
scripts/validate-clients avatar
scripts/validate-web avatar
scripts/smoke-avatar-errors
git status --short

Run the generator twice if determinism matters. The first run updates derived files; the second should produce no diff.

scripts/generate-clients
git diff --exit-code -- generated/

Never use the generated file as the place where two agents negotiate the contract. The next generation run will erase that negotiation.

6. Treat repository instructions as executable authority

Parallel agents frequently conflict because scopes were ambiguous, not because Git was difficult.

A repository-level rule can make authority explicit:

## Shared contract ownership

- `openapi/**` is authoritative for public HTTP schemas.
- `clients/generated/**` is derived; never edit it by hand.
- API-contract tasks integrate before client and UI consumers.
- The API owner approves contract conflicts.
- Every accepted contract change must pass `scripts/check-api-contract`.
- Every generated-client resolution must pass two clean generation runs.

Keep root instructions short and route details to a runbook or script. The goal is not more prose. The goal is that a clean agent session can discover the same authority and run the same proof.

See Repository Harness Patterns for the broader source-of-truth and validation-contract patterns.

7. Validate the conflict boundary and final outcome

A conflict-resolution test should cover the disagreement, not just the edited files.

Proof levelQuestionExample
sourceIs the accepted contract internally valid?OpenAPI validation
producer-consumerDo derived clients match the source?regenerate + compile
local behaviorDoes each affected subsystem work?API and component suites
combined behaviorDoes the real flow work across boundaries?upload-error smoke test
reproducibilityDid tools leave unexplained changes?clean git status --short
recoveryCan a failed transition retry or roll back?migration recovery probe

A useful final evidence record is:

## Conflict resolution — avatar validation errors

### Inputs
- API: `agent/api@4d31...`
- Web: `agent/web@73af...`
- Base: `origin/main@a13f...`

### Classification
Contract conflict plus generated-output conflict.

### Decision
`openapi/avatar.yaml` owns the response shape. Accepted `422` with
`field_errors[]`; UI fixtures and rendering now consume the generated type.

### Resolution
- accepted API schema from the contract branch;
- regenerated TypeScript and Python clients;
- removed hand-authored UI error fixture;
- adapted rendering to the generated error union.

### Evidence
- API contract suite — PASS, 18 tests
- client generation — PASS, second run clean
- TypeScript client compile — PASS
- web typecheck — PASS
- component suite — PASS, 27 tests
- upload-error smoke — PASS
- `git status --short` — clean

### Omitted
Safari multipart flow; no runner in this environment.

### Durable prevention
Client tasks now record the producer schema commit and prohibit edits under
`clients/generated/**`.

This record is a handoff to code review, release automation, or a clean verification agent.

8. Recover when the resolution is wrong

A failed resolution is expected evidence, not a reason to keep editing until the suite turns green.

Use this recovery sequence:

  1. preserve the failed candidate commit, logs, and exact command output;
  2. classify the failed gate;
  3. identify the owning source or worker branch;
  4. restore or recreate the candidate from the last known-good checkpoint;
  5. repair the source branch or canonical instruction;
  6. update its handoff and evidence;
  7. replay every downstream gate whose assumptions changed;
  8. preserve worker branches until final acceptance.

For risky migration or recovery code, inject failures around mutation boundaries and reload persisted state before retrying. A resolution is not recovery-safe if the next process cannot infer what already happened.

Do not delete the evidence-producing failure. Turn it into a regression test, validation script, task-template field, or repository instruction.

9. Prevent the next conflict before cleanup

The final step is not deleting branches. It is repairing the system that allowed ambiguity.

If the conflict began because several workers owned one contract or consumed an undeclared dependency, repair the plan itself. Task Decomposition for Multiple Coding Agents provides the producer-consumer graph, single-owner contract rules, and launch review that prevent the same class of conflict.

Map each conflict to a durable controller:

Observed conflictDurable prevention
two agents edited the same subsystembounded ownership in task envelopes
consumer used a guessed schemaproducer commit recorded in handoff
generated files were hand-mergedgenerated-path rule + clean regeneration check
branches used different basesexact base required at task start and handoff
migrations landed in unsafe orderdependency graph + migration compatibility gate
contradictory instructionsone canonical authority map
locally green branches failed togethermandatory combined outcome check
conflict decision existed only in chatrepository-visible decision record

A repository that learns from conflicts needs fewer heroic integrators over time.

A copyable coding-agent conflict checklist

# Coding-agent conflict-resolution checklist

## Freeze
- [ ] every branch has a stable commit or named patch
- [ ] exact base revisions are recorded
- [ ] working trees are clean or dirty paths are explicit
- [ ] worker evidence, omissions, and risks are preserved

## Reconstruct
- [ ] intended outcome of each branch is understood
- [ ] produced and consumed contracts are identified
- [ ] stale assumptions are visible
- [ ] authoritative source and owner are named

## Classify
- [ ] textual conflict checked
- [ ] contract conflict checked
- [ ] generated-output conflict checked
- [ ] behavior conflict checked
- [ ] migration conflict checked
- [ ] authority conflict checked

## Resolve
- [ ] dedicated candidate starts from an exact clean base
- [ ] accepted behavior is decided before line edits
- [ ] canonical source is resolved first
- [ ] derived files are regenerated, not hand-merged
- [ ] consumers adapt to the accepted contract
- [ ] decision and rationale are recorded

## Prove
- [ ] focused source checks pass
- [ ] producer-consumer boundary checks pass
- [ ] combined user-visible outcome passes
- [ ] retry or rollback is tested where relevant
- [ ] final working tree is clean
- [ ] omitted checks and residual risks are explicit

## Learn
- [ ] regression evidence is preserved
- [ ] ownership, task, handoff, or validation controller is repaired
- [ ] worker branches remain until acceptance
- [ ] cleanup follows repository retention policy

Common bad resolutions

Taking the newest branch

The newest branch may still consume a stale contract. Recency is not authority.

Taking the largest diff

Line count says nothing about ownership or correctness. A one-line schema change can control thousands of generated lines.

Asking a third agent to “make both versions work”

Without explicit authority, the third agent may invent a compromise that satisfies neither contract. Give it the accepted behavior and proof commands first.

Running only the tests that already passed

Those tests proved isolated branches. Add a check that crosses the disputed boundary and a final user-visible outcome test.

Editing generated files until Git is clean

A clean index can still be unreproducible. Resolve the source, regenerate, and require the next generation run to be clean.

Fixing only the integration branch

The source branch, handoff, or repository rule remains wrong. Repair the controller that produced the conflict.

Deleting worktrees immediately

The combined candidate can still fail review or release proof. Keep recoverable worker state until acceptance.

When parallel work should become serial

Stop adding concurrent writers when:

  • the accepted contract is still changing every hour;
  • all tasks edit one tightly coupled subsystem;
  • no owner can decide the disputed behavior;
  • boundary tests do not exist;
  • migrations cannot be retried or rolled back safely;
  • conflict resolution repeatedly costs more than the saved implementation time.

Serial execution is not a failure of multi-agent engineering. It is the correct response when dependencies are stronger than the available contracts and gates.

Conflict resolution is a repository capability

Merge conflicts between coding agents are not primarily a Git problem. They expose missing task boundaries, source-of-truth maps, ownership, dependency order, validation contracts, or durable decisions.

The durable workflow is straightforward: freeze stable checkpoints, reconstruct intent, classify the conflict, choose the authoritative contract, repair the source, regenerate derived output, prove the combined outcome, and move the lesson back into the repository.

repository-harness provides a starting structure for making task boundaries, authority, validation, checkpoints, and evidence handoffs visible to Claude Code, Codex, Cursor, and other coding agents.


FAQ

How should I resolve a merge conflict between coding agents?

Freeze both agent branches at stable commits, reconstruct each branch’s intended outcome and base, classify the conflict, identify the authoritative contract or source, resolve the source rather than only the conflict markers, and rerun focused boundary checks plus combined outcome validation.

Can Git detect every conflict caused by parallel coding agents?

No. Git detects overlapping textual edits, but branches can merge cleanly while disagreeing about schemas, behavior, migrations, generated files, configuration, or repository instructions. These semantic conflicts require contract-aware validation.

Which coding agent should own the conflict resolution?

A designated integrator should own the resolution process. The owner of the affected contract should decide the accepted behavior. The last agent to finish or the agent that touched the most lines should not automatically win.

Should an agent hand-edit generated files during conflict resolution?

No. Resolve the authoritative schema, specification, template, or generator version first, then regenerate the derived files. Hand-merging generated output hides the real disagreement and produces changes that cannot be reproduced.

When should I rebase instead of merge coding-agent branches?

Use the repository’s declared history policy. Rebase can refresh a focused worker branch before integration; merge commits preserve task boundaries and provenance. Neither method resolves semantic disagreement, so contract and outcome checks remain required.

How do I recover from a bad conflict resolution?

Preserve the failed candidate and logs, return to the last known-good integration checkpoint, repair the branch or canonical source that owned the disagreement, update its handoff, and replay the affected integration gates. Keep worker branches until final acceptance.

How can a repository prevent coding-agent merge conflicts?

Declare file and contract ownership, assign bounded task scopes, isolate concurrent writers in worktrees, record exact bases and stable checkpoints, identify producer-consumer dependencies, centralize generated sources, and provide executable validation commands at every shared boundary.