Summary
Add a built-in "AgentTool" that wraps an Engine so a macro agent can delegate to a specialized sub-agent via the existing tool interface. This demonstrates composition, delegation, and structured results, and makes a stronger example than the todo agent.
Motivation
- Composition is a core agent pattern (plan -> delegate -> synthesize).
- The current tool system already provides a clean boundary for sub-tasks.
- This unlocks real workflows (e.g., draft + QA + summarize).
Proposal
Introduce a helper that wraps Engine[ChildState] behind Tool[S]:
// Pseudocode
type AgentTool[S any, C any] struct {
Name string
Description string
Params json.RawMessage
NewState func(parent S, args json.RawMessage) (C, error)
Engine *Engine[C]
Timeout time.Duration
// Optional: ResultMapper to map child result into ToolResult.
}
Behavior
- Each tool call spins up a fresh child state via NewState and a fresh message history inside the child engine.
- The child engine’s output becomes the tool Summary and/or ChatMessage for the macro agent.
- Optional Timeout to avoid long-running child agents.
- No recursion by default (documented guidance to avoid deep nesting).
User Interaction Policy
- Sub-agents should be non-interactive by default.
- If clarification is needed, sub-agents return a structured "needs_user_input" result.
- Macro agent asks the user and re-invokes the sub-agent with the response.
- Sharing the ChatInterface is discouraged (risk of blocking and interleaved messages).
Example Flow
- Macro agent receives: "Write a release note and a support FAQ."
- Macro agent tool-calls:
- ReleaseNoteAgent tool
- FAQAgent tool
- Macro agent synthesizes combined response.
Scope
- Provide a minimal AgentTool implementation and example usage in examples/.
- Document best practices and limits in docs/design.md.
Open Questions
- Should we allow passing shared state explicitly, or only via args?
- Should AgentTool expose a ResultMapper hook?
- How should tool usage be reflected in OnToolDone?
Acceptance Criteria
- A sample macro agent successfully tool-calls a sub-agent and returns results.
- Sub-agent has isolated state and history by default.
- Clear docs on composition and recursion limits.
Summary
Add a built-in "AgentTool" that wraps an Engine so a macro agent can delegate to a specialized sub-agent via the existing tool interface. This demonstrates composition, delegation, and structured results, and makes a stronger example than the todo agent.
Motivation
Proposal
Introduce a helper that wraps Engine[ChildState] behind Tool[S]:
Behavior
User Interaction Policy
Example Flow
Scope
Open Questions
Acceptance Criteria