a2a-rust — Agent2Agent (A2A) Protocol SDK for Rust

Introduction

a2a-rust is a pure Rust implementation of the Agent2Agent (A2A) protocol — an open standard for connecting AI agents over the network. It is written against the v1.0.1 specification; the version carried on the wire is 1.0, since §3.6 excludes patch numbers from requests, responses and Agent Cards.

If you're building AI agents that need to talk to each other, discover capabilities, delegate tasks, and stream results — this library gives you the full protocol stack with zero unsafe code, compile-time type safety, and production-grade hardening.

What is the A2A Protocol?

The Agent2Agent protocol defines how AI agents discover, communicate with, and delegate work to each other. Think of it as HTTP for AI agents: a shared language that lets any agent talk to any other, regardless of implementation.

The protocol defines:

  • Agent Cards — Discovery documents describing what an agent can do
  • Tasks — Units of work with well-defined lifecycle states
  • Messages — Structured payloads carrying text, data, or binary content
  • Streaming — Real-time progress via Server-Sent Events (SSE)
  • Push Notifications — Webhook delivery for async results

Why Rust?

Rust gives you performance, safety, and correctness without compromise:

  • Zero-cost abstractions — Trait objects, generics, and async/await with no runtime overhead
  • No unsafe — The entire codebase is free of unsafe code
  • Thread safety at compile time — All public types implement Send + Sync
  • Exhaustive pattern matching — The compiler catches missing protocol states
  • Production-ready — Battle-tested HTTP via hyper, robust error handling, no panics on any caller input or I/O failure

Architecture at a Glance

a2a-rust is organized as a Cargo workspace with four crates:

┌─────────────────────────────────────────────┐
│  a2a-protocol-sdk                           │
│  umbrella re-exports + prelude              │
├──────────────────────┬──────────────────────┤
│  a2a-protocol-client │  a2a-protocol-server │
│  HTTP client         │  agent framework     │
├──────────────────────┴──────────────────────┤
│  a2a-protocol-types                         │
│  wire types, serde, no I/O                  │
└─────────────────────────────────────────────┘
CratePurpose
a2a-protocol-typesAll A2A wire types with serde serialization. Pure data — no I/O, no async.
a2a-protocol-clientHTTP client for calling remote A2A agents. Supports JSON-RPC and REST transports, plus WebSocket and gRPC behind feature flags.
a2a-protocol-serverServer framework for building A2A agents. Pluggable stores, interceptors, and dispatchers.
a2a-protocol-sdkUmbrella crate that re-exports everything with a convenient prelude module.

Key Features

  • Full v1.0 wire types — Every A2A type with correct JSON serialization
  • Quad transport — JSON-RPC 2.0, REST, WebSocket (websocket feature flag), and gRPC (grpc feature flag), both client and server
  • SSE streaming — Real-time SendStreamingMessage and SubscribeToTask
  • Push notifications — Pluggable PushSender with SSRF protection
  • Agent card discovery — Static and dynamic card handlers with HTTP caching (ETag, Last-Modified, 304)
  • Pluggable storesTaskStore and PushConfigStore traits with in-memory, SQLite, PostgreSQL, and tenant-aware backends
  • Multi-tenancyTenantAwareInMemoryTaskStore, TenantAwareSqliteTaskStore, and TenantAwarePostgresTaskStore with full tenant isolation
  • Interceptor chains — Client and server middleware for auth, logging, metrics, rate limiting
  • Rate limiting — Built-in RateLimitInterceptor with per-caller fixed-window limiting
  • Client retry — Configurable RetryPolicy with exponential backoff for transient failures
  • Server startup helperserve() reduces ~25 lines of hyper boilerplate to one call
  • Request ID propagationCallContext::request_id auto-extracted from X-Request-ID header
  • Task store metricsTaskStore::count() for monitoring and capacity management
  • Task state machine — Validated transitions per the A2A specification
  • Executor ergonomicsboxed_future, agent_executor! macro, EventEmitter reduce boilerplate
  • Executor timeout — Kills hung agent tasks automatically
  • CORS support — Configurable cross-origin policies
  • Fully configurable — All defaults (timeouts, limits, intervals) are overridable via builders
  • Mutation-tested — Zero surviving mutants enforced via cargo-mutants CI gate
  • No panics on fallible paths — Every operation that can fail on input, network, or storage errors returns Result; the only expect calls in library code assert internal invariants (e.g. lock-poisoning propagation) that no caller input can trigger

All 11 Protocol Methods

MethodDescription
SendMessageSynchronous message send; returns completed task
SendStreamingMessageStreaming send with real-time SSE events
GetTaskRetrieve a task by ID
ListTasksQuery tasks with filtering and pagination
CancelTaskRequest cancellation of a running task
SubscribeToTaskRe-subscribe to an existing task's event stream
CreateTaskPushNotificationConfigRegister a webhook for push delivery
GetTaskPushNotificationConfigRetrieve a push config by ID
ListTaskPushNotificationConfigsList all push configs for a task
DeleteTaskPushNotificationConfigRemove a push config
GetExtendedAgentCardFetch authenticated agent card

What's Next?