Examples Overview

The examples/ directory contains standalone binary crates that demonstrate real-world usage of the a2a-rust SDK. Each example builds and runs independently.

At a Glance

ExampleDescriptionExternal depsDifficulty
Hello AgentSmallest complete agent — 28 lines of code above its tests, the SDK plus tokio, no SDK feature flagsNoneBeginner
Deploy AgentThe hello agent made shippable — env config, /healthz and /readyz, SIGTERM draining, a container and a Kubernetes manifestNoneBeginner
Incident-Response TeamMulti-turn input-required, delegation, streaming, cancellationNone (optional local model)Intermediate
Echo AgentEvery A2A method over all four bindings, with a coverage matrix that fails the run on a gapNoneBeginner
Agent Team4-agent team with 102 E2E tests on its default feature set (the dogfood CI job runs them)NoneAdvanced
Genai AgentLLM-powered agent using genai (OpenAI, Anthropic, Gemini, Ollama, etc.)A local model server, or an API keyIntermediate
Rig AgentReal rig-core agent behind A2A — hosted or fully local, no mockNone (local server works keyless)Intermediate
MCP AgentAn agent whose tools come from an MCP server it discovers at startupNone (optional tool-capable local model)Intermediate
A2A → MCP BridgeExposes a remote A2A agent as an MCP serverNoneIntermediate
Multi-Language TeamRust coordinator delegating to Python, JS, Go, Java and Rust A2A agentsWorker agentsAdvanced

Where to Start

  • New to A2A? Start with the Hello Agent — the entire agent fits on one screen. Then read the Echo Agent for the complete request lifecycle across four bindings.

  • Evaluating the SDK? Run the Agent Team — it runs 102 automated end-to-end tests across the SDK's features and prints a pass/fail report.

  • Integrating an LLM? See the Genai Agent or Rig Agent for patterns that bridge LLM frameworks with A2A's AgentExecutor trait.

  • Cross-language interop? See the Multi-Language Team for a Rust coordinator that talks to agents in 4 other languages.

Common Pattern

Every example that serves A2A follows the same three-step integration pattern:

use a2a_protocol_sdk::prelude::*;
use std::sync::Arc;

// 1. Implement AgentExecutor. The macro writes the impl; the trait's real
//    signature returns Pin<Box<dyn Future>> to stay object-safe.
struct MyExecutor;

agent_executor!(MyExecutor, |ctx, queue| async {
    let emit = EventEmitter::new(ctx, queue);
    emit.status(TaskState::Working).await?;
    // ... do work ...
    emit.artifact("result", vec![Part::text("done")], None, Some(true)).await?;
    emit.status(TaskState::Completed).await?;
    Ok(())
});

fn main() -> Result<(), Box<dyn std::error::Error>> {
// 2. Build a handler
let handler = Arc::new(RequestHandlerBuilder::new(MyExecutor).build()?);

// 3. Serve via any dispatcher
let dispatcher = JsonRpcDispatcher::new(handler);
// or: RestDispatcher, A2aRouter (Axum), gRPC
let _ = dispatcher;
Ok(())
}

For details on each step, see The AgentExecutor Trait, Request Handler & Builder, and Dispatchers.