Skip to content

Use case

Multi-Agent Orchestration ​

Compose multiple specialised agents that hand off tasks, share context, and collaborate on complex workflows.

  • Stack Agent SDK + Agent Server
  • Pattern Agents · Orchestration
  • Read ~9 min

Overview ​

Complex tasks often benefit from multiple specialised agents working together. Cognipeer's Agent SDK supports multi-agent patterns where agents can delegate, hand off, and collaborate — all while maintaining deterministic control and full tracing.

This guide builds a content pipeline with Researcher, Writer, and Reviewer agents.

When to reach for this use case

If your team needs the capabilities described above and you would rather build on proven primitives than wire one from scratch — this is the shape to start from.

Architecture ​

Agent SDK handles each agent's runtime independently with its own tools, system prompt, and constraints. Agents communicate through the serving layer.

Agent Server registers all agents, manages their conversations, and provides the API surface for orchestration.

1. Create Specialised Agents ​

Define each agent with its own tools and expertise, then expose explicit handoff targets for controlled delegation.

typescript
import { createSmartAgent, createTool } from "@cognipeer/agent-sdk";
import { z } from "zod";

// Researcher agent — gathers information
const researcher = createSmartAgent({
  name: "Researcher",
  model,
  tools: [searchWeb, extractData],
  systemPrompt: "You are a research specialist. Gather comprehensive information on the given topic. Output structured findings.",
  useTodoList: true,
  limits: { maxToolCalls: 8 },
  tracing: { enabled: true },
});

// Writer agent — creates content
const writer = createSmartAgent({
  name: "Writer",
  model,
  tools: [formatMarkdown, generateOutline],
  systemPrompt: "You are a technical writer. Take research findings and produce well-structured, clear content.",
  limits: { maxToolCalls: 5 },
  tracing: { enabled: true },
});

// Reviewer agent — quality check
const reviewer = createSmartAgent({
  name: "Reviewer",
  model,
  tools: [checkFacts, scoringTool],
  systemPrompt: "You are a content reviewer. Check accuracy, clarity, and completeness. Provide actionable feedback.",
  limits: { maxToolCalls: 5 },
  tracing: { enabled: true },
});

const orchestrator = createSmartAgent({
  name: "Orchestrator",
  model,
  tools: [intakeClassifier],
  handoffs: [
    researcher.asHandoff({
      toolName: "handoff_to_researcher",
      description: "Transfer the conversation to the research specialist",
    }),
    writer.asHandoff({
      toolName: "handoff_to_writer",
      description: "Transfer the task to the writer agent",
    }),
    reviewer.asHandoff({
      toolName: "handoff_to_reviewer",
      description: "Transfer the draft to the reviewer agent",
    }),
  ],
  systemPrompt: "Route each request to the right specialist and use handoff tools when ownership should move to another agent.",
  tracing: { enabled: true },
});

2. Register All Agents ​

Expose each agent through Agent Server, each with its own endpoint.

typescript
import {
  createAgentServer,
  createPostgresProvider,
} from "@cognipeer/agent-server";

const server = createAgentServer({
  basePath: "/api/agents",
  storage: createPostgresProvider({
    connectionString: process.env.DATABASE_URL!,
  }),
  swagger: { enabled: true, path: "/docs" },
});

server.registerSDKAgent("researcher", researcher, {
  description: "Gathers and structures research data",
});

server.registerSDKAgent("writer", writer, {
  description: "Produces written content from research",
});

server.registerSDKAgent("reviewer", reviewer, {
  description: "Reviews content for quality",
});

server.registerSDKAgent("orchestrator", orchestrator, {
  description: "Routes work across specialist agents with explicit handoffs",
});

3. Orchestrate The Pipeline And Handoffs ​

You can still run a fixed pipeline, but the more flexible pattern is a controller agent that moves ownership between specialists with handoff tools.

typescript
const result = await orchestrator.invoke({
  messages: [
    {
      role: "user",
      content: "Research AI agent architectures in 2025, write a short article, then send it for review.",
    },
  ],
  onEvent(event) {
    if (event.type === "handoff") {
      console.log("handoff", event.from, "->", event.to, event.toolName);
    }
  },
});

console.log(result.content);
console.log(result.state?.toolHistory);

Result ​

You now have a multi-agent content pipeline that:

  • Specialises each agent for its task (research, writing, review)
  • Routes work dynamically through explicit handoff tools
  • Traces every agent execution and handoff event independently
  • Serves each agent as its own REST endpoint
  • Persists all conversations and outputs in the database
  • Scales as you add more specialist agents and delegation rules

Products used ​

This pattern combines 2 Cognipeer products.

See every pattern on the use case index, or browse all Cognipeer libraries.

Studio · Pulse · Console · Agent SDK and more — the Cognipeer documentation hub