Multi-Agent 오케스트레이션
언제 멀티 에이전트가 필요한가?
섹션 제목: “언제 멀티 에이전트가 필요한가?”단일 에이전트는 컨텍스트 윈도우 한계, 도구 다양성 한계, 단일 실행 스레드 한계를 가집니다. 다음 상황에서 멀티 에이전트가 필요합니다:
- 태스크가 단일 컨텍스트 윈도우를 초과하는 경우
- 전문화된 에이전트가 각 도메인을 더 잘 처리하는 경우
- 독립적 태스크를 병렬로 실행해야 하는 경우
- 검증을 별도 에이전트가 독립적으로 수행해야 하는 경우
패턴 1: Supervisor (중앙 집중 조율)
섹션 제목: “패턴 1: Supervisor (중앙 집중 조율)”Supervisor 패턴에서는 중앙 에이전트(Supervisor)가 하위 에이전트들에게 태스크를 배분하고 결과를 통합합니다.
┌─────────────┐ │ Supervisor │ ← 사용자 요청 └──────┬──────┘ ┌───────────┼───────────┐ ↓ ↓ ↓┌───────┐ ┌───────┐ ┌───────┐│Agent A│ │Agent B│ │Agent C││(코드) │ │(테스트)│ │(문서) │└───────┘ └───────┘ └───────┘ └───────────┴───────────┘ ↓ 결과 통합 및 반환class SupervisorAgent:
def run(self, goal: str) -> str: # 태스크 분해 subtasks = self.llm.decompose(goal)
results = {} for subtask in subtasks: # 적합한 하위 에이전트 선택 agent = self.route_to_agent(subtask) results[subtask.id] = agent.run(subtask.description)
# 결과 통합 return self.llm.synthesize(goal, results)
def route_to_agent(self, subtask: Subtask) -> Agent: routing = { "code": self.code_agent, "test": self.test_agent, "docs": self.docs_agent, } return routing[subtask.type]적합한 상황:
- 태스크 유형이 명확히 구분되는 경우
- 중앙 조율이 필요한 복잡한 워크플로우
- 결과를 통합해야 하는 경우
주의사항: Supervisor가 단일 장애점(SPOF)이 됩니다. Supervisor 자체의 품질이 전체 시스템을 결정합니다.
패턴 2: Peer-to-Peer (직접 핸드오프)
섹션 제목: “패턴 2: Peer-to-Peer (직접 핸드오프)”P2P 패턴에서는 에이전트들이 서로 직접 핸드오프합니다. 중앙 조율자가 없고 각 에이전트가 다음 에이전트를 결정합니다.
Agent A → (핸드오프) → Agent B → (핸드오프) → Agent C ↑ │ └─────────────── (피드백 루프) ─────────────────┘@dataclassclass HandoffMessage: from_agent: str to_agent: str content: str metadata: dict
class PeerAgent: def run(self, message: HandoffMessage) -> HandoffMessage | None: result = self.process(message.content)
# 다음 에이전트 결정 next_agent = self.determine_next(result) if next_agent is None: return None # 파이프라인 종료
return HandoffMessage( from_agent=self.name, to_agent=next_agent, content=result, metadata={"previous": message.metadata}, )적합한 상황:
- 선형 파이프라인 (A → B → C)
- 각 단계의 책임이 명확한 경우
- 에이전트 추가/제거가 자주 필요한 경우
패턴 3: Hierarchical (계층 구조)
섹션 제목: “패턴 3: Hierarchical (계층 구조)”Hierarchical 패턴은 트리 구조로 에이전트를 조직합니다. 상위 에이전트가 하위 에이전트를 관리하고, 하위 에이전트는 다시 더 하위 에이전트를 가질 수 있습니다.
┌──────────────┐ │ Coordinator │ Level 0 └──────┬───────┘ ┌─────────┴─────────┐ ↓ ↓ ┌──────────┐ ┌──────────┐ │ Manager A│ │ Manager B│ Level 1 └────┬─────┘ └────┬─────┘ ┌────┴────┐ ┌────┴────┐ ↓ ↓ ↓ ↓Worker1 Worker2 Worker3 Worker4 Level 2적합한 상황:
- 대규모 복잡 태스크 (대형 코드베이스 전체 리팩토링)
- 도메인별 전문화가 필요한 경우
- 병렬 실행과 조율이 동시에 필요한 경우
패턴 비교
섹션 제목: “패턴 비교”| 기준 | Supervisor | Peer-to-Peer | Hierarchical | |---|---|---|---| | 복잡도 | 중간 | 낮음 | 높음 | | 확장성 | 제한적 | 높음 | 매우 높음 | | 디버깅 용이성 | 중간 | 높음 | 낮음 | | 병렬 실행 | 가능 | 제한적 | 매우 용이 | | 단일 장애점 | 있음 | 없음 | 있음 (각 레벨) | | 적합 규모 | 중소형 | 소형 | 대형 |
멀티 에이전트 설계 원칙
섹션 제목: “멀티 에이전트 설계 원칙”상호운용성: A2A와 Agent Skills
섹션 제목: “상호운용성: A2A와 Agent Skills”MCP가 호스트 애플리케이션과 도구·데이터의 연결을 표준화한다면, A2A(Agent-to-Agent) 는 독립적으로 배포된 에이전트가 능력을 알리고, 태스크를 위임하고, 상태와 산출물을 교환하는 계약을 다룬다. 내부 함수 호출을 A2A로 바꿀 필요는 없다. 서로 다른 팀·런타임·신뢰 경계를 넘는 에이전트를 연결할 때 후보가 된다.
사용자 → 오케스트레이터 ── A2A 태스크 위임 ──► 외부 전문 에이전트 │ │ └──── MCP 도구 호출 ────────────────┘Agent Skills는 에이전트가 특정 업무를 일관되게 수행하도록 만드는 SKILL.md 중심의 재사용 묶음이다. 지침뿐 아니라 스크립트·참조 자료·템플릿을 포함할 수 있다. A2A가 “누구에게 어떤 태스크를 맡길지”의 통신 계약이라면, Skills는 “그 에이전트가 어떤 절차와 자원을 사용할지”의 작업 계약이다. 둘 다 권한·입력·출력·버전을 명시해야 안전하게 재사용할 수 있다.
1. 최소 에이전트 원칙
섹션 제목: “1. 최소 에이전트 원칙”필요 이상으로 에이전트를 추가하지 마세요. 에이전트가 늘어날수록 오케스트레이션 복잡도가 기하급수적으로 증가합니다.
2. 명확한 인터페이스
섹션 제목: “2. 명확한 인터페이스”에이전트 간 통신은 구조화된 형태로 정의하세요.
@dataclassclass AgentMessage: task_id: str content: str context: dict expected_output_format: str # 출력 형식 명시3. 격리와 독립성
섹션 제목: “3. 격리와 독립성”각 에이전트는 가능한 한 독립적으로 작동해야 합니다. 공유 상태를 최소화하고, 각 에이전트가 자체 완결적인 컨텍스트를 갖도록 설계하세요.
# 나쁜 패턴: 공유 전역 상태shared_state = {}
# 좋은 패턴: 메시지 패싱def agent_b(message_from_a: AgentMessage) -> AgentMessage: # message_from_a에만 의존, 전역 상태 없음 result = process(message_from_a.content) return AgentMessage(task_id=message_from_a.task_id, content=result)Multi-Agent 오케스트레이션은 Supervisor(중앙 조율), P2P(직접 핸드오프), Hierarchical(계층 구조) 세 가지 핵심 패턴으로 구성됩니다. 패턴 선택은 태스크 규모, 병렬화 필요성, 디버깅 용이성을 기준으로 합니다. 조직·런타임 경계를 넘는 위임은 A2A, 반복 가능한 업무 절차는 Agent Skills를 검토할 수 있습니다. 최소 에이전트 원칙과 명확한 인터페이스가 안정적인 시스템의 기반입니다.
Section 02 학습을 완료했습니다. 다음 Section 03에서는 세 축 중 첫 번째인 Context Engineering을 심화 학습합니다.