Project 13: Multi-Agent Shared Memory

Build a memory system that enables multiple AI agents to share, update, and coordinate through a common knowledge graph with conflict resolution and access control.

Quick Reference

Attribute Value
Difficulty Level 4: Expert
Time Estimate 2-3 weeks (35-45 hours)
Language Python
Prerequisites Projects 1-12, distributed systems, concurrency
Key Topics Multi-agent systems, shared state, conflict resolution, access control, event sourcing, eventual consistency

1. Learning Objectives

By completing this project, you will:

  1. Design shared memory architectures for multi-agent systems.
  2. Implement conflict detection and resolution strategies.
  3. Build access control for agent-specific views.
  4. Handle concurrent memory updates safely.
  5. Create event sourcing for memory audit trails.

2. Theoretical Foundation

2.1 Core Concepts

  • Shared Memory: A knowledge graph accessible by multiple agents, enabling collaboration and information sharing.

  • Conflict Resolution: Strategies for handling when two agents update the same fact differently:
    • Last-write-wins (simple but loses data)
    • Merge (combine both if possible)
    • Timestamp-based (most recent fact wins)
    • Confidence-weighted (higher confidence wins)
  • Access Control: Agents may have different permissions:
    • Read-only vs read-write
    • Namespace isolation
    • Role-based access
  • Event Sourcing: Store all changes as events, enabling replay, audit, and undo.

  • Eventual Consistency: In distributed systems, all agents eventually see the same state.

2.2 Why This Matters

Modern AI applications often involve multiple agents:

  • Research agent + Writing agent + Review agent
  • Customer service agent + Escalation agent + Specialist agent

These agents need to share context, coordinate actions, and avoid stepping on each other’s updates.

2.3 Common Misconceptions

  • “Agents can share a simple database.” Race conditions and conflicts need careful handling.
  • “Last-write-wins is fine.” You lose important information from overwritten facts.
  • “Each agent should have separate memory.” Duplication and inconsistency become problems.

2.4 ASCII Diagram: Multi-Agent Shared Memory

MULTI-AGENT SHARED MEMORY ARCHITECTURE
══════════════════════════════════════════════════════════════

┌─────────────────────────────────────────────────────────────┐
│                       AGENTS                                 │
├─────────────────────────────────────────────────────────────┤
│                                                              │
│  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐         │
│  │  Research   │  │   Writer    │  │   Review    │         │
│  │   Agent     │  │   Agent     │  │   Agent     │         │
│  │             │  │             │  │             │         │
│  │  Permissions│  │  Permissions│  │  Permissions│         │
│  │  - R/W facts│  │  - R/W docs │  │  - Read all │         │
│  │  - R topics │  │  - R facts  │  │  - W reviews│         │
│  └──────┬──────┘  └──────┬──────┘  └──────┬──────┘         │
│         │                │                │                 │
└─────────┼────────────────┼────────────────┼─────────────────┘
          │                │                │
          ▼                ▼                ▼
┌─────────────────────────────────────────────────────────────┐
│                    MEMORY GATEWAY                            │
├─────────────────────────────────────────────────────────────┤
│                                                              │
│  ┌─────────────────────────────────────────────────────┐    │
│  │                 ACCESS CONTROL                       │    │
│  │                                                      │    │
│  │  Agent: Research                                     │    │
│  │    - Can write: facts, entities, relationships      │    │
│  │    - Can read: topics, summaries                    │    │
│  │    - Namespace: research/*                          │    │
│  └─────────────────────────────────────────────────────┘    │
│                          │                                   │
│                          ▼                                   │
│  ┌─────────────────────────────────────────────────────┐    │
│  │               CONFLICT RESOLVER                      │    │
│  │                                                      │    │
│  │  Strategy: confidence_weighted + timestamp           │    │
│  │                                                      │    │
│  │  Conflict Detected:                                 │    │
│  │    Agent A: "Budget is $100K" (conf: 0.8, t1)       │    │
│  │    Agent B: "Budget is $150K" (conf: 0.9, t2)       │    │
│  │                                                      │    │
│  │  Resolution: Keep B (higher confidence, newer)      │    │
│  │  Archive: A marked as superseded                    │    │
│  └─────────────────────────────────────────────────────┘    │
│                          │                                   │
└──────────────────────────┼──────────────────────────────────┘
                           │
                           ▼
┌─────────────────────────────────────────────────────────────┐
│                   SHARED KNOWLEDGE GRAPH                     │
├─────────────────────────────────────────────────────────────┤
│                                                              │
│  ┌─────────────────────────────────────────────────────┐    │
│  │  Entities and Relationships                         │    │
│  │                                                      │    │
│  │  (Project_Alpha)───[HAS_BUDGET]───▶(Budget: $150K)  │    │
│  │        │                              │              │    │
│  │        │                         [UPDATED_BY]        │    │
│  │        │                              │              │    │
│  │   [ASSIGNED_TO]                       ▼              │    │
│  │        │                     (Agent: Writer)         │    │
│  │        ▼                                            │    │
│  │  (Team: Engineering)                                │    │
│  └─────────────────────────────────────────────────────┘    │
│                                                              │
│  ┌─────────────────────────────────────────────────────┐    │
│  │  Event Log (Append-Only)                            │    │
│  │                                                      │    │
│  │  t1: [Research] CREATED entity "Project_Alpha"      │    │
│  │  t2: [Research] CREATED relationship ASSIGNED_TO    │    │
│  │  t3: [Writer] CREATED entity "Budget: $100K"        │    │
│  │  t4: [Review] UPDATED "Budget" to "$150K"           │    │
│  │       (conflict with t3, resolved: supersede)       │    │
│  └─────────────────────────────────────────────────────┘    │
│                                                              │
└─────────────────────────────────────────────────────────────┘


CONFLICT RESOLUTION STRATEGIES
══════════════════════════════

1. LAST-WRITE-WINS (Simple)
   ─────────────────────────
   Agent A writes: "Budget = $100K" at t1
   Agent B writes: "Budget = $150K" at t2
   Result: Budget = $150K (t2 > t1)
   Problem: Agent A's info lost without record

2. CONFIDENCE-WEIGHTED
   ────────────────────
   Agent A writes: "Budget = $100K" (confidence: 0.7)
   Agent B writes: "Budget = $150K" (confidence: 0.9)
   Result: Budget = $150K (0.9 > 0.7)
   Benefit: Higher quality info preserved

3. MERGE (When Possible)
   ──────────────────────
   Agent A writes: "Alice works on API"
   Agent B writes: "Alice works on Frontend"
   Result: "Alice works on API, Frontend"
   Requirement: Facts must be non-contradictory

4. AGENT AUTHORITY
   ────────────────
   Research Agent: Authority on facts
   Writer Agent: Authority on documents
   Result: Each agent's domain takes precedence


NAMESPACE ISOLATION EXAMPLE
═══════════════════════════

┌─────────────────────────────────────────────────────────────┐
│ Namespace: research/*                                        │
│   Owner: Research Agent                                      │
│   Contents:                                                  │
│     - research/findings/market_analysis                     │
│     - research/entities/competitors                         │
│     - research/facts/industry_trends                        │
│   Access:                                                    │
│     - Research Agent: R/W                                   │
│     - Writer Agent: Read-only                               │
│     - Review Agent: Read-only                               │
└─────────────────────────────────────────────────────────────┘

┌─────────────────────────────────────────────────────────────┐
│ Namespace: documents/*                                       │
│   Owner: Writer Agent                                        │
│   Contents:                                                  │
│     - documents/drafts/proposal_v1                          │
│     - documents/final/proposal                              │
│   Access:                                                    │
│     - Writer Agent: R/W                                     │
│     - Research Agent: No access                             │
│     - Review Agent: Read-only + can add comments            │
└─────────────────────────────────────────────────────────────┘

3. Project Specification

3.1 What You Will Build

A Python framework that:

  • Provides shared memory access for multiple agents
  • Implements conflict detection and resolution
  • Supports namespace isolation and access control
  • Records all changes as events

3.2 Functional Requirements

  1. Register agent: memory.register_agent(agent_id, permissions)
  2. Write fact: memory.write(agent_id, fact, namespace) → Result
  3. Read facts: memory.read(agent_id, query, namespace) → List[Fact]
  4. Detect conflict: memory.check_conflict(fact) → Conflict None
  5. Resolve conflict: memory.resolve(conflict, strategy) → Resolution
  6. Get event log: memory.get_events(since, agent_id) → List[Event]
  7. Replay state: memory.replay_to(timestamp) → State

3.3 Example Usage / Output

from shared_memory import SharedMemory, Agent, Permissions

# Initialize shared memory
memory = SharedMemory(
    conflict_strategy="confidence_weighted",
    event_store=event_db
)

# Register agents
research_agent = memory.register_agent(
    agent_id="research",
    permissions=Permissions(
        write=["facts/*", "entities/*"],
        read=["*"],
    )
)

writer_agent = memory.register_agent(
    agent_id="writer",
    permissions=Permissions(
        write=["documents/*"],
        read=["facts/*", "entities/*"],
    )
)

# Research agent writes a fact
result = memory.write(
    agent_id="research",
    fact=Fact(
        subject="Project_Alpha",
        predicate="has_budget",
        object="$100,000",
        confidence=0.8
    ),
    namespace="facts"
)
print(f"Written: {result.fact_id}")

# Writer agent tries to update the same fact
result = memory.write(
    agent_id="writer",
    fact=Fact(
        subject="Project_Alpha",
        predicate="has_budget",
        object="$150,000",
        confidence=0.9
    ),
    namespace="facts"
)

if result.conflict:
    print(f"Conflict detected: {result.conflict}")
    print(f"Resolution: {result.resolution}")
    # Conflict detected: Existing fact has different value
    # Resolution: SUPERSEDED (new fact has higher confidence)

# Both agents read current state
for agent_id in ["research", "writer"]:
    facts = memory.read(agent_id, query="Project_Alpha budget")
    print(f"{agent_id} sees: {facts[0].object}")
# research sees: $150,000
# writer sees: $150,000

# Get event history
events = memory.get_events(agent_id="research")
for event in events:
    print(f"[{event.timestamp}] {event.agent}: {event.action} {event.subject}")
# [t1] research: CREATED Project_Alpha has_budget $100,000
# [t2] writer: UPDATED Project_Alpha has_budget $150,000 (superseded t1)

# Writer tries to access research namespace (denied)
try:
    memory.write(
        agent_id="writer",
        fact=Fact(...),
        namespace="entities"  # Writer doesn't have write access
    )
except PermissionDenied as e:
    print(f"Access denied: {e}")

4. Solution Architecture

4.1 High-Level Design

┌───────────────┐     ┌───────────────┐
│    Agents     │────▶│   Gateway     │
└───────────────┘     └───────┬───────┘
                              │
                    ┌─────────┴─────────┐
                    │                   │
                    ▼                   ▼
            ┌───────────────┐   ┌───────────────┐
            │    Access     │   │   Conflict    │
            │   Control     │   │   Resolver    │
            └───────────────┘   └───────────────┘
                    │                   │
                    └─────────┬─────────┘
                              │
                    ┌─────────┴─────────┐
                    │                   │
                    ▼                   ▼
            ┌───────────────┐   ┌───────────────┐
            │  Graph Store  │   │  Event Store  │
            └───────────────┘   └───────────────┘

4.2 Key Components

Component Responsibility Technology
Gateway Route requests, enforce access Python class
AccessControl Permission checking Rule engine
ConflictResolver Detect and resolve conflicts Strategy pattern
GraphStore Store facts and relationships Neo4j
EventStore Append-only event log SQLite/Postgres

4.3 Data Models

from pydantic import BaseModel
from datetime import datetime
from typing import Literal

class Permissions(BaseModel):
    read: list[str]  # Glob patterns
    write: list[str]  # Glob patterns

class Agent(BaseModel):
    id: str
    name: str
    permissions: Permissions

class Fact(BaseModel):
    subject: str
    predicate: str
    object: str
    confidence: float = 1.0
    source_agent: str | None = None

class Conflict(BaseModel):
    existing_fact: Fact
    new_fact: Fact
    conflict_type: Literal["value", "confidence", "deleted"]

class Resolution(BaseModel):
    action: Literal["keep_existing", "supersede", "merge", "reject"]
    resulting_fact: Fact
    rationale: str

class Event(BaseModel):
    id: str
    timestamp: datetime
    agent_id: str
    action: Literal["created", "updated", "deleted", "superseded"]
    fact: Fact
    previous_fact: Fact | None = None

5. Implementation Guide

5.1 Development Environment Setup

mkdir shared-memory && cd shared-memory
python -m venv .venv && source .venv/bin/activate
pip install neo4j pydantic sqlalchemy

5.2 Project Structure

shared-memory/
├── src/
│   ├── memory.py          # SharedMemory main class
│   ├── gateway.py         # Request routing
│   ├── access.py          # Access control
│   ├── conflicts.py       # Conflict resolution
│   ├── stores/
│   │   ├── graph.py       # Graph storage
│   │   └── events.py      # Event storage
│   └── models.py          # Data models
├── tests/
│   ├── test_access.py
│   ├── test_conflicts.py
│   └── test_integration.py
└── README.md

5.3 Implementation Phases

Phase 1: Basic Shared Access (10-12h)

Goals:

  • Multiple agents can read/write to shared graph
  • Basic permission checking

Tasks:

  1. Build Gateway class for request routing
  2. Implement basic access control
  3. Create shared graph store
  4. Test multi-agent read/write

Checkpoint: Multiple agents share a single graph.

Phase 2: Conflict Resolution (12-15h)

Goals:

  • Conflict detection working
  • Multiple resolution strategies

Tasks:

  1. Implement conflict detection on write
  2. Build resolution strategies (LWW, confidence, merge)
  3. Add conflict resolution hooks
  4. Test concurrent update scenarios

Checkpoint: Conflicts detected and resolved correctly.

Phase 3: Event Sourcing + Polish (10-12h)

Goals:

  • Full event audit trail
  • State replay capability

Tasks:

  1. Implement event store
  2. Add event logging on all operations
  3. Build state replay from events
  4. Add namespace isolation

Checkpoint: Complete multi-agent memory system.


6. Testing Strategy

6.1 Test Categories

Category Purpose Examples
Unit Test components Access control rules
Integration Test multi-agent flows Concurrent writes
Stress Test under load 100 agents, 1000 writes

6.2 Critical Test Cases

  1. Permission enforcement: Unauthorized writes rejected
  2. Conflict detection: Same fact updated by two agents
  3. Resolution correctness: Winning fact is expected one
  4. Event completeness: All changes logged

7. Common Pitfalls & Debugging

Pitfall Symptom Solution
Race conditions Lost updates Add locking or versioning
Permission gaps Unexpected access Test all permission combinations
Event ordering Inconsistent replay Use monotonic timestamps
Namespace overlap Cross-agent pollution Strict namespace validation

8. Extensions & Challenges

8.1 Beginner Extensions

  • Add agent activity dashboard
  • Implement undo/redo via events

8.2 Intermediate Extensions

  • Add real-time sync via WebSocket
  • Implement optimistic concurrency

8.3 Advanced Extensions

  • Add distributed consensus (Raft)
  • Implement CRDT-based merging

9. Real-World Connections

9.1 Industry Applications

  • AutoGPT/CrewAI: Multi-agent coordination
  • LangGraph: Shared state machines
  • Enterprise AI: Team-based agent systems

9.2 Interview Relevance

  • Explain conflict resolution strategies
  • Discuss event sourcing benefits
  • Describe distributed consistency models

10. Resources

10.1 Essential Reading

  • “Designing Data-Intensive Applications” by Kleppmann — Ch. on Distributed Data
  • Event Sourcing Pattern — Martin Fowler
  • “AI Engineering” by Chip Huyen — Ch. on Multi-Agent Systems
  • Previous: Project 12 (Hybrid Retrieval)
  • Next: Project 14 (Production Memory Service)

11. Self-Assessment Checklist

  • I understand conflict detection and resolution strategies
  • I can implement access control with namespaces
  • I know how event sourcing enables audit trails
  • I understand eventual consistency tradeoffs

12. Submission / Completion Criteria

Minimum Viable Completion:

  • Multi-agent read/write working
  • Basic conflict detection
  • Permission enforcement

Full Completion:

  • Multiple resolution strategies
  • Event logging complete
  • Namespace isolation

Excellence:

  • State replay from events
  • Distributed consensus
  • Production performance