Unlike all other frameworks, communication flows in Agency Swarm are not hierarchical or sequential. Instead, they are uniform, which means you can define them in any way you want.

Understanding the Orchestrator Pattern

Agency Swarm implements an orchestrator pattern where agents use other agents as tools through the SendMessage mechanism. This is fundamentally different from sequential handoffs:
  • Control always returns to the calling agent - When Agent A calls Agent B, Agent B processes the request and returns a response to Agent A
  • Agents act as specialized tools - Each agent can be thought of as a specialized tool that another agent can invoke
  • Orchestrator agents coordinate workflows - Typically, one agent orchestrates the entire workflow by calling multiple other agents and compiling their responses

Example: Investment Research Platform

# Portfolio Manager orchestrates investment research using output_type for structured responses
portfolio_manager = Agent(
    name="PortfolioManager",
    instructions="Orchestrate investment research by gathering data, delegating analysis, and compiling recommendations",
    tools=[fetch_market_data],
)

risk_analyst = Agent(
    name="RiskAnalyst",
    instructions="Specialize in investment risk analysis",
    tools=[analyze_risk_factors],
    output_type=RiskAssessment,  # Structured output
)

# New structure: entry points as positional args, communication flows as keyword arg
agency = Agency(
    portfolio_manager,  # Entry point and orchestrator
    communication_flows=[
        (portfolio_manager, risk_analyst),     # Portfolio Manager can request risk analysis
        (portfolio_manager, report_generator), # Portfolio Manager can request report generation
    ]
)
In this example, the Portfolio Manager needs responses from both specialists to make an informed investment decision. The RiskAnalyst provides structured risk assessment data using output_type, and control always returns to the Portfolio Manager who compiles the final recommendation.Updated version of the framework now also supports > and < symbols to define communication flows in a more intuitive and readable way.

Defining Your Own Communication Flows

from agency_swarm import Agency

# New structure with explicit communication flows
agency = Agency(
    ceo, dev,  # Entry points - agents that can communicate with users
    communication_flows=[
        (ceo, dev),   # CEO can initiate communication with Developer
        (ceo > va),   # CEO can initiate communication with Virtual Assistant
        (va < dev)    # Developer can initiate communication with Virtual Assistant
        # Or using a single line:
        # (va < ceo > dev > va),
    ]
)

Communication Flow Patterns

Communication flows are established using explicit tuples in the communication_flows parameter. Each tuple defined as either (sender, receiver) or (sender > receiver) or (receiver < sender) defines a directional communication path. Entry points are defined as positional arguments to the Agency constructor.The CEO can initiate communication and send tasks to the Developer and the Virtual Assistant, and they can respond back in the same thread, but the Developer or VA cannot initiate a conversation and assign tasks to the CEO.All agents added as entry points can talk to the user. You can add as many levels of communication as you want.

Under the Hood

Agency Swarm uses a special SendMessage tool to allow agents to communicate with each other. By defining communication flows, it adds new recipients to the SendMessage function. If you’d like to modify the behavior of this tool, you can do so by creating your own Custom Communication Flows (Advanced). It’s important to understand that each defined communication flow establishes a distinct context for interaction. When the SendMessage tool is invoked by a sender agent (e.g., CEO) to a recipient agent (e.g., Developer), this happens within a dedicated conversation thread specific to that CEO-Developer pair. In this thread, the sender agent effectively takes on the role of a “user,” and the recipient agent responds as the “assistant.” This ensures that the history and context of communication between any two agents are isolated and maintained separately for each specific flow.