a2a_agent.go
Overview
This file implements a remote agent interface using the Agent-To-Agent (A2A) protocol, enabling communication with agents running in separate processes or hosts. It provides a proxy agent that translates local agent invocation context sessions into A2A protocol messages, sends these messages over the network, and streams back the remote agent's responses as session events. This allows seamless integration of remote agents within the local agent framework while abstracting networking and protocol details.
The core functionality includes:
Resolution of remote agent metadata (agent card) from a URL or local file.
Creation of an A2A client for communication based on the resolved agent card.
Conversion of local session events to A2A messages for transmission.
Streaming reception of A2A events transformed back into session events.
Error handling and enrichment of session events with custom metadata.
Support for message sending with attached configuration options.
This file implements the remote agent proxy as an instance of agent.Agent, conforming to the local agent lifecycle and invocation model.
Types and Functions
A2AConfig
type A2AConfig struct {
Name string
Description string
AgentCard *a2a.AgentCard
AgentCardSource string
CardResolveOptions []agentcard.ResolveOption
ClientFactory *a2aclient.Factory
MessageSendConfig *a2a.MessageSendConfig
}
Description:
Configuration struct to describe and configure a remote A2A agent.
Fields:
Name: Human-readable name of the agent.Description: Description of the agent's purpose.AgentCard: Optional pre-loaded agent card metadata describing the remote agent.AgentCardSource: URL or local file path to load the agent card ifAgentCardis not provided.CardResolveOptions: Resolver options applied when fetching the agent card via URL.ClientFactory: Optional factory for creating customized A2A clients.MessageSendConfig: Configuration attached to each message sent to the remote agent.
Usage Example:
cfg := A2AConfig{
Name: "RemoteLLMAgent",
AgentCardSource: "https://example.com/agent_card.json",
MessageSendConfig: &a2a.MessageSendConfig{ /* ... */ },
}
agent, err := NewA2A(cfg)
NewA2A
func NewA2A(cfg A2AConfig) (agent.Agent, error)
Description:
Factory function that creates a remote A2A agent implementing the agent.Agent interface. It requires either a resolved AgentCard or an AgentCardSource URL/path to function.
Parameters:
cfg: AnA2AConfigstruct describing remote agent metadata and client creation parameters.
Returns:
An
agent.Agentinstance that communicates with the remote agent.An error if neither
AgentCardnorAgentCardSourceis provided or initialization fails.
Usage:
Use this function to instantiate and register a remote agent proxy that delegates invocations via the A2A protocol.
Type a2aAgent
type a2aAgent struct {
resolvedCard *a2a.AgentCard
}
Description:
Internal struct implementing the remote agent logic. Holds the resolved agent card to avoid repeated resolution.
Method a2aAgent.run
func (a *a2aAgent) run(ctx agent.InvocationContext, cfg A2AConfig) iter.Seq2[*session.Event, error]
Description:
Runs the remote agent invocation. This method performs the following steps:
Resolves the remote agent's agent card if not already done.
Creates an A2A client to communicate with the remote agent.
Constructs an A2A message from the invocation context's session events.
Sends the message using streaming RPC and receives streamed A2A events.
Converts incoming A2A events into session events and yields them.
Handles errors by yielding special error events.
Parameters:
ctx: Invocation context providing session and state information.cfg: Configuration parameters for the remote agent.
Returns:
A generator function that yields session events or errors, supporting asynchronous streaming of remote agent responses.
Usage:
This method is invoked internally when the agent is run via the ADK agent lifecycle.
resolveAgentCard
func resolveAgentCard(ctx agent.InvocationContext, cfg A2AConfig) (*a2a.AgentCard, error)
Description:
Resolves the remote agent's AgentCard metadata either by:
Returning the provided
AgentCardfrom config.Fetching and resolving the card from an HTTP(S) URL.
Reading and unmarshaling the card from a local JSON file.
Parameters:
ctx: Invocation context (used for resolution operations).cfg: Configuration holdingAgentCardorAgentCardSource.
Returns:
The resolved AgentCard or an error if resolution or parsing fails.
Important Implementation Detail:
Local file-based resolution reads the entire file and unmarshals JSON into an a2a.AgentCard pointer.
newMessage
func newMessage(ctx agent.InvocationContext) (*a2a.Message, error)
Description:
Constructs a new A2A message from the invocation context’s session events. It inspects the session event history to:
Detect if the last user event is a function call, converting it into a message with appropriate task and context IDs.
Otherwise, construct a message from missing remote session parts.
Parameters:
ctx: Invocation context holding the session and event history.
Returns:
An
a2a.Messagerepresenting the user input or function call.An error if conversion fails.
Usage:
Called internally before sending a message to the remote agent.
toErrorEvent
func toErrorEvent(ctx agent.InvocationContext, err error) *session.Event
Description:
Creates a session event representing an error state, embedding the error message in the event and custom metadata. This event is yielded to signal problems in remote communication or invocation.
Parameters:
ctx: Invocation context to associate the error event with the current session.err: The error to encapsulate.
Returns:
A session event containing the error details.
updateCustomMetadata
func updateCustomMetadata(event *session.Event, request *a2a.MessageSendParams, response a2a.Event)
Description:
Augments a session event's custom metadata with serialized forms of the A2A request and response messages. This aids debugging and telemetry by preserving raw protocol data.
Parameters:
event: The session event to update.request: The original A2A message send parameters.response: The received A2A event response.
Implementation Detail:
Uses a converter utility to transform requests into map structures, handling serialization errors gracefully.
destroy
func destroy(client *a2aclient.Client)
Description:
Safely destroys the A2A client, ignoring destruction errors (with a TODO note to add logging).
Parameters:
client: The A2A client to destroy.
Important Implementation Details
Agent Card Resolution: Supports multiple sources for agent metadata allowing flexible deployment (local files or remote HTTP URLs).
Streaming Communication: Utilizes streaming RPC (
SendStreamingMessage) for asynchronous, incremental message exchange, supporting real-time remote agent interaction.Session Event Conversion: Relies on external utilities (Event Conversion and Processing) to convert between ADK session events and A2A protocol events.
Error Handling as Events: Rather than returning errors directly, errors in resolution, client creation, or messaging are converted into special session events that can be handled as part of the normal event stream.
Custom Metadata Enrichment: All session events emitted include metadata linking back to the original A2A protocol messages for enhanced observability.
Client Factory Usage: Supports pluggable client creation for different communication configurations or authentication schemes.
Contextual Message Creation: Detects function calls in the invocation context to form messages correctly with task and context identifiers, preserving invocation semantics.
Resource Cleanup: Ensures client resources are released after invocation, preventing resource leaks.
Interaction with Other Parts of the System
Agent Framework Integration: Implements the
agent.Agentinterface, seamlessly integrating with the agent lifecycle and invocation context (Agent Invocation Context, AI Agent Framework).A2A Client Library: Uses
a2aclientfor protocol communication, which handles low-level networking and serialization.Session and Event Management: Operates on session events to build messages and process responses, interacting with Session Management.
Event Conversion Utilities: Delegates event serialization and deserialization to the conversion utilities in
Event Conversion and Processing.Remote Agent Discovery: Leverages agent card resolution mechanisms to dynamically discover and configure remote agents (Agent Skill Building).
Error Reporting and Telemetry: Enriches session events with metadata for telemetry and debugging (Telemetry and Observability).
Visual Diagram
sequenceDiagram
participant LocalA2AAgent as Local A2A Agent
participant Client as A2A Client
participant RemoteAgent as Remote Agent Server
LocalA2AAgent->>LocalA2AAgent: Resolve AgentCard (URL/File)
LocalA2AAgent->>Client: Create client from AgentCard
LocalA2AAgent->>LocalA2AAgent: Convert InvocationContext events to A2A Message
LocalA2AAgent->>Client: SendStreamingMessage(Message)
Client->>RemoteAgent: Transmit A2A Message (gRPC/HTTP)
RemoteAgent->>RemoteAgent: Process message, generate events
RemoteAgent->>Client: Stream A2A Events (responses)
Client->>LocalA2AAgent: Receive streamed events
LocalA2AAgent->>LocalA2AAgent: Convert A2A Events to Session Events
LocalA2AAgent->>Caller: Yield session events (stream)
This sequence diagram illustrates the lifecycle of an invocation through the remote A2A agent proxy, showing agent card resolution, client creation, message sending, event streaming, conversion, and yielding back to the invoking caller.
References to Related Topics
For detailed protocol message formats and streaming event handling, see Remote Agent Communication (A2A).
For session event and A2A event conversion methods, see Event Conversion and Processing.
For agent lifecycle and invocation context interfaces, see Agent Invocation Context and AI Agent Framework.
For client creation and network communication details, see the
a2aclientpackage referenced in this file.For telemetry and metadata enrichment approaches, see Telemetry and Observability.
For remote agent skill discovery and agent card composition, see Agent Skill Building.
This file is a core component enabling distributed multi-agent orchestration by bridging local invocation with remote agent communication through the A2A protocol.