> ## Documentation Index
> Fetch the complete documentation index at: https://agno-v2.mintlify.site/llms.txt
> Use this file to discover all available pages before exploring further.

# A2A

> Expose Agno agents via the A2A protocol

v2.1.2 (Introduced in v2.1.2)

The [Agent-to-Agent Protocol (A2A)](https://a2a-protocol.org/latest/topics/what-is-a2a/) is an open standard for agents to communicate with each other.

Agno integrates with A2A, enabling Agno agents and teams to be exposed in an A2A-compatible format.

The `A2A` interface works with the [AgentOS](https://agno-v2.mintlify.site/agent-os/introduction.md) runtime to provide this functionality.

## Setup

Set `a2a_interface=True` when creating an `AgentOS` instance:

```python a2a_agentos.py theme={null}
from agno.agent import Agent
from agno.os import AgentOS

agent = Agent(name="My Agno Agent", id="my_agent")

agent_os = AgentOS(
    agents=[agent],
    a2a_interface=True,
)
app = agent_os.get_app()

if __name__ == "__main__":
    agent_os.serve(app="a2a_agentos:app", reload=True)
```

By default, all local agents, teams, and workflows in the AgentOS are exposed via A2A. Remote instances (`RemoteAgent`, `RemoteTeam`, `RemoteWorkflow`) are excluded from this default.

Specific agents, teams, and workflows can be exposed by initializing the interface explicitly:

```python a2a_interface_initialization.py theme={null}
from agno.agent import Agent
from agno.os import AgentOS
from agno.os.interfaces.a2a import A2A

agent = Agent(name="My Agno Agent", id="my_agent")

# Initialize the A2A interface specifying the agents to expose
a2a = A2A(agents=[agent])

agent_os = AgentOS(
    agents=[agent],
    interfaces=[a2a], # Pass the A2A interface to the AgentOS using the `interfaces` parameter
)
app = agent_os.get_app()

if __name__ == "__main__":
    agent_os.serve(app="a2a_interface_initialization:app", reload=True)
```

## A2A Endpoints

For each available agent, team and workflow, the following A2A-compatible endpoints will be available:

### Agents

* `/a2a/agents/{id}/.well-known/agent-card.json`:
  Returns the [Agent Card](https://a2a-protocol.org/v0.3.0/topics/agent-discovery/#1-well-known-uri) describing the agent in A2A format.
  See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/get-agent-card.md).

* `/a2a/agents/{id}/v1/message:stream`:
  Runs the agent, streaming the responses as events in A2A format.
  See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/stream-message-agent.md) and [A2A protocol docs](https://a2a-protocol.org/v0.3.0/specification/#356-method-mapping-reference-table).

* `/a2a/agents/{id}/v1/message:send`:
  Runs the agent, returning the response in A2A format (non-streaming).
  See [A2A protocol docs](https://a2a-protocol.org/v0.3.0/specification/#356-method-mapping-reference-table).

### Teams

* `/a2a/teams/{id}/.well-known/agent-card.json`:
  Returns the Team Card describing the Team in A2A format. See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/get-team-card.md).

* `/a2a/teams/{id}/v1/message:stream`:
  Runs the team, streaming the responses as events in A2A format. See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/stream-message-team.md) and [A2A protocol docs](https://a2a-protocol.org/v0.3.0/specification/#356-method-mapping-reference-table).

* `/a2a/teams/{id}/v1/message:send`:
  Runs the team, returning the response in A2A format (non-streaming). See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/run-message-team.md).

### Workflows

* `/a2a/workflows/{id}/.well-known/agent-card.json`:
  Returns the Workflow Card describing the Workflow in A2A format. See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/get-workflow-card.md).

* `/a2a/workflows/{id}/v1/message:stream`:
  Runs the workflow, streaming the responses as events in A2A format. See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/stream-message-workflow.md) and [A2A protocol docs](https://a2a-protocol.org/v0.3.0/specification/#356-method-mapping-reference-table).

* `/a2a/workflows/{id}/v1/message:send`:
  Runs the workflow, returning the response in A2A format (non-streaming). See [API reference](https://agno-v2.mintlify.site/reference-api/schema/a2a/run-message-workflow.md).

> [!NOTE]
>
> A2A clients expect a server to expose only a single agent.
> To use your Agno A2A interface with those clients, use `/a2a/agents/{id}/` (or `/a2a/teams/{id}/`, `/a2a/workflows/{id}/`) as the base URL.

## Authorization

With [authorization](https://agno-v2.mintlify.site/agent-os/security/authorization/overview.md) enabled, A2A routes sit behind the same JWT verification and scope checks as the REST API. Send the token as `Authorization: Bearer <token>`.

| A2A method | Agents | Teams | Workflows |
| - | - | - | - |
| `.well-known/agent-card.json` | `agents:read` | `teams:read` | `workflows:read` |
| `message:send` / `message:stream` | `agents:run` | `teams:run` | `workflows:run` |
| `tasks:get` | `agents:read` | `teams:read` | Not exposed |
| `tasks:cancel` | `agents:run` | `teams:run` | Not exposed |

Per-resource scopes apply through the A2A prefix: a token with `agents:my-agent:run` can call `POST /a2a/agents/my-agent/v1/message:send`. See [Scopes](https://agno-v2.mintlify.site/agent-os/security/authorization/scopes.md) for the full route-to-scope mapping.

### Run identity

For anonymous callers, the `X-User-ID` header and the `userId` field in `params.message.metadata` attribute the run to a user. Authenticated callers are pinned to their token's principal, and any client-supplied identity is ignored. Anonymous callers cannot claim reserved principals (`sa:*`, `__scheduler__`).

### Task ownership

`tasks:get` requires `contextId` (the session the run belongs to) and returns `400` without it. For callers scoped to a user (a service account, or a JWT user under [user isolation](https://agno-v2.mintlify.site/agent-os/security/authorization/user-isolation.md)), `tasks:get` and `tasks:cancel` verify that the task belongs to that user in that session. `tasks:cancel` also requires `contextId` for these callers.

> [!WARNING]
>
> Before v2.7, A2A routes were mounted outside the AgentOS auth middleware and accepted unauthenticated requests even with `authorization=True`. v2.7 moves A2A behind the unified auth layer. If your deployment relied on open A2A endpoints, mint credentials with the scopes above for those callers before upgrading.

## Connecting to A2A Servers

Agno provides two ways to connect to A2A-compatible servers:

### Using A2AClient

For direct A2A protocol access:

```python theme={null}
from agno.client.a2a import A2AClient

client = A2AClient("http://localhost:7003/a2a/agents/my-agent")
result = await client.send_message(
    message="Hello!",
    headers={"Authorization": f"Bearer {token}"},  # Required when the server enforces authorization
)
```

See [A2A Client](https://agno-v2.mintlify.site/agent-os/client/a2a-client.md) for full documentation.

### Using RemoteAgent

For a higher-level agent interface:

```python theme={null}
from agno.agent import RemoteAgent

agent = RemoteAgent(
    base_url="http://localhost:7003",
    agent_id="my-agent",
    protocol="a2a",
)
response = await agent.arun("Hello!", auth_token=token)  # auth_token required when the server enforces authorization
```

See [RemoteAgent Reference](https://agno-v2.mintlify.site/reference/agents/remote-agent.md) for full documentation.

## Developer Resources

* [AgentOS Reference](https://agno-v2.mintlify.site/reference/agent-os/agent-os.md)
* [A2A Client Documentation](https://agno-v2.mintlify.site/agent-os/client/a2a-client.md)
* [A2A Protocol Documentation](https://a2a-protocol.org/latest/)
* [Examples](https://agno-v2.mintlify.site/agent-os/usage/interfaces/a2a/basic.md)


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.