4.1 KiB
4.1 KiB
Agent Team Collaboration Architecture
System Design
Shared Blackboard Pattern
type SharedBoard struct {
mu sync.RWMutex
entries []BoardEntry
}
type BoardEntry struct {
Author string
Content string
Type string // "draft" | "challenge"
}
Thread-safe operations:
Add(): Appends entries with write lockToContext(): Reads all entries with read lock, formats as XML
Execution Flow
HandleUserMessage()
↓
Master Planning Loop (iteration 0-4)
├─ Master analyzes user request
├─ Outputs ASSIGN:member:task lines
├─ parseAssignments() extracts tasks
├─ Creates new SharedBoard{}
│
├─ runMembersParallel()
│ ├─ For each assignment, spawn goroutine
│ ├─ Each member sees current board snapshot
│ ├─ Member executes task
│ ├─ Result added to board as "draft"
│ └─ WaitGroup ensures all complete
│
├─ runChallengeRound()
│ ├─ Filter members with CanChallenge=true
│ ├─ For each challenger, spawn goroutine
│ ├─ Challenger sees full board
│ ├─ Outputs CHALLENGE:... or AGREE
│ ├─ CHALLENGE entries added to board
│ └─ WaitGroup ensures all complete
│
├─ Master Review
│ ├─ Receives board.ToContext()
│ ├─ Sees all drafts and challenges
│ ├─ Decides: DONE or re-ASSIGN
│ └─ Loop continues if re-ASSIGN
│
└─ updateMasterMemory() (async)
Concurrency Model
Parallel Execution Phase:
var wg sync.WaitGroup
for memberName, task := range assignments {
wg.Add(1)
go func(name, t string) {
defer wg.Done()
// Execute task
board.Add(name, result, "draft")
}(memberName, task)
}
wg.Wait() // Wait for all members
Challenge Round Phase:
var wg sync.WaitGroup
for _, name := range challengers {
wg.Add(1)
go func(n string) {
defer wg.Done()
// Review board
if strings.Contains(result, "CHALLENGE:") {
board.Add(n, result, "challenge")
}
}(name)
}
wg.Wait() // Wait for all challenges
Context Injection
Initial Draft Phase:
Member System Prompt = Soul + Memory + [empty board]
Challenge Round Phase:
Member System Prompt = Soul + Memory + <team_board>
<entry type="draft" author="member1">...</entry>
<entry type="draft" author="member2">...</entry>
</team_board>
Master Review Phase:
Master Feedback = Team results + <team_board>
<entry type="draft" author="member1">...</entry>
<entry type="draft" author="member2">...</entry>
<entry type="challenge" author="member1">...</entry>
</team_board>
Event Streaming
Events emitted during execution:
-
Parallel Phase:
EvtAgentMessagewithrole: "member"(streaming)EvtTaskAssign(task assignment)EvtWorkspaceFile(if document generated)
-
Challenge Phase:
EvtAgentMessagewithrole: "challenge"(streaming)
-
Status Updates:
EvtRoomStatuswithstatus: "working"→"thinking"→"pending"
Configuration
Agent AGENT.md:
---
name: agent_name
role: member
can_challenge: true # Enable challenge participation
---
Agent SOUL.md:
- Includes challenge instructions
- Specifies how to output
CHALLENGE:... - Defines acceptance of challenges
Benefits
- Parallelism: Members work simultaneously, not sequentially
- Transparency: All members see each other's work via board
- Quality Control: Challenge round catches issues early
- Collaboration: Members can question and improve each other's work
- Master Awareness: Master sees full context before deciding
- Thread-Safe: Concurrent access protected by mutexes
- Scalable: Works with any number of members
Backward Compatibility
- Existing master/member roles unchanged
- Challenge role is additive (new event type)
- Members without
can_challenge: trueskip challenge round - No breaking changes to existing APIs