Skip to main content

Conflicts

Every add() runs a same-namespace nearest-neighbour search before persisting. If a near-duplicate is found above the conflict threshold, memledger records the conflict on the new record and emits a CONFLICTS edge into the chain store linking the new record to its near-duplicate.

What counts as a conflict

A new record is conflicting if, in the same namespace, an existing record has cosine similarity ≥ conflict_threshold (default 0.65). The threshold is configurable per backend and per call.

What happens on conflict

By default, memledger writes the new record and the CONFLICTS edge — neither claim is silently overwritten. The detected conflicts are exposed on the new MemoryRecord itself:

record = await ml.get(memory_id)
for c in record.conflicts:
print(c.existing_id, c.similarity, c.resolution)

Resolution behavior is configured via a ConflictResolverStrategy (see Conflict detection). Built-in resolutions are strings: "store_anyway" (default), "supersede", "merge", "accept_both", "reject_new".

Why this matters

Multi-agent systems generate contradictory memories all the time — Agent A says "scale to 50", Agent B says "scale to 100" five minutes later. Without conflict detection, both end up in the vector store and search() retrieves whichever ranks higher by cosine similarity. With conflict detection, the contradiction is visible in the trust graph, and your resolver gets to decide what semantic the system holds.

In the UI

In the UI Console, conflicts render as red edges in the trust graph — visible at a glance.