Agent protocols: A complete guide to MCP, A2A, and ACP

The explosion of AI agents that lack shared language has created a problem for developers. We now have thousands of specialized, powerful agents that can’t talk to one another. The result is brittle data silos, fragmented workflows, and a massive loss of compounding value. If a financial-analysis agent can’t coordinate with an inventory-management agent, for example, the ceiling on what either can do is low.

Just as HTTP and REST standardized web communication and unlocked decades of innovation, an emerging layer of open agent communication protocols is doing the same for AI. Major technology vendors (Google, IBM, Microsoft, AWS, Cisco, Salesforce, ServiceNow, SAP) are actively building these standards, and the space is consolidating under the Linux Foundation.

This guide is for developers, architects, and engineering leads who need to navigate agentic AI protocols. It covers: 

  • The practical difference between model and agent protocols
  • A spec-accurate technical comparison of the Model Context Protocol (MCP) and the now-unified Agent2Agent (A2A) protocol
  • How to architect systems with them together
  • The security practices required to operate them in production

The state of agent protocols in 2026: Consolidation under the Linux Foundation

The current landscape is defined by consolidation around open standards. After a period of competing specifications, the industry has converged on two protocols for two different jobs: one for AI applications talking to tools and another for agents talking to each other. This simplifies architectural decisions and accelerates the building of a genuinely interoperable agent ecosystem.

From three standards to two: How ACP folded into A2A

The most significant recent development is the consolidation of agent-to-agent protocols. In August 2025, IBM Research and Google announced that IBM’s Agent Communication Protocol (ACP) would join forces with Google’s Agent2Agent Protocol (A2A) under the Linux Foundation’s LF AI & Data umbrella

ACP development is now winding down; its assets and expertise are being contributed directly to A2A. Kate Blair (IBM Research, who led ACP) joined the A2A Technical Steering Committee, alongside representatives from Google, Microsoft, AWS, Cisco, Salesforce, ServiceNow, and SAP.

For developers, this consolidation produces a clear division of labor:

  • Model Context Protocol (MCP): The standard for model-to-tool communication. It’s how an AI application or agent connects to data sources, tools, and workflows.
  • Unified A2A: The standard for agent-to-agent communication. It absorbs ACP’s stateful, asynchronous concepts and remains the spec to use for cross-team or cross-vendor agent collaboration.

BeeAI users (the IBM platform that originally shipped ACP) have a migration path via the A2AServer and A2AAgent adapters, plus an official BeeAI: ACP to A2A migration guide. ACP repos and docs continue to exist for historical reference, but new work should target A2A.

Foundational concepts: Model protocols vs agent protocols

The fundamental differences between MCP and A2A are their scope and purpose. 

  • MCP defines the narrow interface between an AI application and its external tools, such as a specific API, database, or workflow. 
  • A2A defines a broader framework for how independent agents discover, interact, and collaborate to achieve a common goal.

Model Context Protocol (MCP): The universal adapter for tools

The MCP docs describe it as a USB-C port for AI applications. That is, a single, predictable interface that lets any MCP-compliant AI client connect to any MCP-compliant tool server. It standardizes how data sources (files, databases), tools (search engines, calculators), and workflows (specialized prompts) are exposed to AI applications.

Technically, MCP is a JSON-RPC 2.0 specification carried over one of two transports:

  • stdio: The client launches the MCP server as a subprocess and exchanges newline-delimited JSON-RPC over stdin/stdout. Most local MCP servers (filesystem, Git, databases, IDE plug-ins) ship in this form. No network attack surface.
  • Streamable HTTP: A single HTTP endpoint that handles POST plus optional Server-Sent Events for server-to-client streaming. This replaced the older HTTP+SSE transport from protocol version 2024-11-05.

Every MCP session starts with an initialize/initialized handshake that negotiates protocol version and capabilities. After the handshake, the client typically calls tools/list, resources/list, and prompts/list to discover what the server offers. Discovery is fully dynamic, not pre-configured. The server can also notify the client when its toolset changes (notifications/tools/list_changed).

Here is a correct MCP tool invocation. Note that every tool is called through the same tools/call method, with the specific tool addressed by name:

MCP request:

{

  “jsonrpc”: “2.0”,

  “id”: 2,

  “method”: “tools/call”,

  “params”: {

    “name”: “get_weather”,

    “arguments”: { “location”: “New York” }

  }

}

MCP response:

{

  “jsonrpc”: “2.0”,

  “id”: 2,

  “result”: {

    “content”: [

      { “type”: “text”, “text”: “Current weather in New York: 72°F, Partly cloudy” }

    ],

    “isError”: false

  }

}

Tools also declare a structured inputSchema (JSON Schema) and optionally an outputSchema for validated structured results. Authorization for remote MCP servers is defined separately in the MCP Authorization spec, which uses OAuth 2.1 flows.

Agent2Agent Protocol (A2A): The language of collaboration

A2A is a specification for agent-to-agent communication over a client-server protocol with fluid roles, enabling any autonomous agent to discover, delegate tasks to, and receive results from another regardless of who initiated the relationship. Where MCP connects an application to a tool, A2A connects a team of specialist agents, potentially across organizations or frameworks.

A2A reached v1.0 in 2026 and is governed under the Linux Foundation. The v1.0 spec is explicitly layered:

  • Canonical data model: AgentCard, AgentSkill, Task, Message, Part, Artifact (defined in Protobuf, also published as JSON Schema 2020-12).
  • Abstract operations: SendMessage, SendStreamingMessage, GetTask, ListTasks, CancelTask, SubscribeToTask, plus push-notification config methods.
  • Protocol bindings: JSON-RPC 2.0 (primary), gRPC, and HTTP+JSON/REST. Each interface in the Agent Card advertises its own protocolBinding.

Agents expose their capabilities through a public Agent Card served at /.well-known/agent-card.json (per RFC 8615). The card declares name, version, supportedInterfaces[] (url + protocolBinding), capabilities flags (streaming, pushNotifications, extendedAgentCard), skills[] (each with id, name, description, tags, examples, inputModes, outputModes), and security schemes. In production, the card SHOULD also carry signatures. AgentCardSignature uses JWS (RFC 7515) over a canonicalized (JCS, RFC 8785) version of the card so clients can detect tampering.

Agent Communication Protocol (ACP): Stateful, long-running workflows

IBM Research launched ACP in March 2025 to power its BeeAI Platform (an open-source platform for agent interoperability). ACP introduced concepts around persistent state for long-running tasks, asynchronous interaction, and reliability for mission-critical enterprise workflows. In August 2025, ACP officially joined forces with A2A under LF AI & Data.

The long-running orchestration pattern that ACP championed is now native to A2A. Conceptually:

import asyncio

from a2a.client import A2ACardResolver, ClientConfig, create_client

from a2a.types import Role, SendMessageRequest

from a2a.helpers import new_text_message

 

async def process_insurance_claim(claim_id: str):

    print(f”[{claim_id}] Starting claim process…”)

 

    # Delegate to a DocumentAnalysisAgent (could take minutes).

    doc_agent = await resolve_and_open(“https://doc-analyzer.internal.corp”)

    await doc_agent.send_message(SendMessageRequest(

        message=new_text_message(f”Analyse documents for claim {claim_id}”, role=Role.ROLE_USER)

    ))

 

    # Delegate to a FraudDetectionAgent (could take hours; uses A2A push notifications).

    fraud_agent = await resolve_and_open(“https://fraud-detector.internal.corp”)

    await fraud_agent.send_message(SendMessageRequest(

        message=new_text_message(f”Run fraud check on claim {claim_id}”, role=Role.ROLE_USER)

    ))

 

    print(f”[{claim_id}] Claim processing complete.”)

The reliability features that distinguished ACP (task persistence, async resumption, and webhook-based progress) are all part of A2A v1.0 today.

Technical deep dive: MCP and A2A side by side

MCP and A2A differ in scope, transport, state model, and discovery. Both protocols are JSON-RPC at the message level; the real distinctions are about what each is for and how each models long-running work.

Model Context Protocol (MCP)Agent2Agent protocol (A2A)
Core purposeStandardize model-to-tool communication (AI apps using data sources, tools, workflows)Standardize agent-to-agent collaboration and task delegation across organizations
Message formatJSON-RPC 2.0JSON-RPC 2.0 (primary); spec also defines gRPC and HTTP+JSON/REST bindings
Transportsstdio (local subprocess) or Streamable HTTP (remote single endpoint with POST plus optional SSE)HTTPS for JSON-RPC and HTTP+REST, and HTTP/2 for gRPC, with each interface advertising its binding in the Agent Card
State modelSession-stateful: initialize/initialized handshake, MCP-Session-Id, server-to-client notifications, list-change eventsTask-stateful: every long-running interaction is a Task with explicit states (SUBMITTED → WORKING → COMPLETED/FAILED/CANCELED/REJECTED/INPUT_REQUIRED/AUTH_REQUIRED)
DiscoveryDynamic, in-session: tools/list, resources/list, prompts/list after handshake; notifications/tools/list_changedStatic well-known URI plus curated registries: clients GET /.well-known/agent-card.json or query a vetted registry
AuthAuthorization spec defines OAuth 2.1 flows for remote serversAgentCard.securitySchemes plus security (OpenAPI-style); supports API Key, OAuth 2.0, OIDC, mTLS
Typical use caseA coding agent reading files via an MCP filesystem server, or querying a database via an MCP serverAn orchestrator agent delegating a complex analysis task to a specialist agent built in another framework

Communication style

Both protocols use JSON-RPC 2.0 to carry messages. MCP’s transports are stdio (local) or Streamable HTTP (remote). A2A’s bindings are JSON-RPC 2.0 (most common), gRPC, or HTTP+JSON/REST.

The substantive difference is what the JSON-RPC messages represent: 

  • In MCP, a single client/server session is the unit of state: you initialize, you call tools/list and tools/call, and the session persists until you tear it down. 
  • In A2A, each long-running interaction is a Task with an explicit state machine (SUBMITTED → WORKING → COMPLETED/FAILED/CANCELED/REJECTED/INPUT_REQUIRED/AUTH_REQUIRED). You can attach an SSE stream to a Task or subscribe to push notifications, and you can resume by polling GetTask.

State management: Who holds the context?

Both protocols are stateful, but at different scopes.

MCP session state includes the negotiated protocol version, the set of advertised tools/resources/prompts (which can change mid-session), and any server notifications. Sessions on Streamable HTTP are tagged with an MCP-Session-Id header that the client must include on every subsequent request. The host application (the MCP client) and the server both retain context across calls.

A2A state is task-scoped. Every long-running interaction creates a Task identified by a server-assigned taskId. The server stores the Task’s state, history, and artifacts; the client polls GetTask, attaches an SSE stream, or registers a webhook to receive updates.

Discovery and capabilities

MCP discovery is dynamic and in-session. After initialization, the client calls tools/list, resources/list, and prompts/list. The server can later emit notifications/tools/list_changed when the toolset changes, prompting the client to refresh.

A2A discovery uses three strategies (per the Agent Discovery topic page in the spec):

  • Well-known URI: Clients GET https://<agent-domain>/.well-known/agent-card.json. Best for public agents.
  • Curated registry: A central registry holds vetted Agent Cards. Best for enterprise marketplaces.
  • Direct configuration: Hardcoded URLs/config files. Fine for tightly-coupled internal systems.

How to architect and build multi-agent systems

The two protocols compose cleanly. A high-level orchestrator agent uses A2A to manage workflows and delegate to specialist agents; each specialist agent then uses MCP internally to call its own tools (databases, APIs, file systems). The orchestrator only needs to know what specialists can do (their A2A Agent Cards), not how they do it; the specialists encapsulate tool interactions behind their MCP integrations.

The layered architecture: Using protocols together

Conceptual flow (a KYC orchestration):

  • User submits an onboarding request to the Orchestrator Agent.
  • Orchestrator sends an A2A SendMessage call to the KYC Agent’s well-known endpoint, delegating the verification.
  • KYC Agent uses MCP servers internally, one for the credit-check API, one for ID verification, invoking tools/call with the right tool name plus arguments.
  • KYC Agent synthesizes results into a Task COMPLETED state and returns artifacts to the Orchestrator.
  • Orchestrator returns the final response to the user.

Implementation pattern 1: A financial agent for data enrichment

Use case: An onboarding agent verifies a new user’s identity by cross-referencing multiple data sources.

Architecture (using the official a2a-sdk on the orchestrator side and an MCP client inside the KYC specialist):

# Orchestrator (Onboarding_Agent) using the official a2a-sdk

import httpx

from a2a.client import A2ACardResolver, ClientConfig, create_client

from a2a.types import Role, SendMessageRequest

from a2a.helpers import new_text_message

 

async def handle_onboarding(user_id: str):

    async with httpx.AsyncClient() as h:

        resolver = A2ACardResolver(httpx_client=h, base_url=”https://kyc-agent.internal.corp”)

        card = await resolver.get_agent_card()

        client = await create_client(agent=card, client_config=ClientConfig(streaming=False))

        request = SendMessageRequest(

            message=new_text_message(f”Verify identity for user {user_id}”, role=Role.ROLE_USER)

        )

        async for event in client.send_message(request):

            if hasattr(event, ‘status’) and event.status.state == “TASK_STATE_COMPLETED”:

                return event  # carries final artifacts

 

# Specialist (KYC_Agent) using an MCP client internally

from mcp import ClientSession

from mcp.client.streamable_http import streamablehttp_client

 

async def verify_identity(user_id: str):

    async with streamablehttp_client(“https://credit-check.internal.corp/mcp”) as (read, write, _):

        async with ClientSession(read, write) as session:

            await session.initialize()

            result = await session.call_tool(“credit_check”, {“user_id”: user_id})

            # result.content is a list of typed content blocks

    # Same pattern for the ID verification MCP server.

    return {“status”: “verified”}  # or “failed” based on tool outputs

Note the asymmetry: the orchestrator speaks A2A (one verb, SendMessage, with a Message carrying Parts). The specialist speaks MCP (initialize, then tools/call per tool). Neither side needs to know the other’s internal implementation.

Implementation pattern 2: An e-commerce chatbot with inventory management

Use case: A customer asks a support chatbot to check stock for a product, then initiate a return for a previous order.

  • The Chatbot Agent handles the user conversation. When the user asks “Is the blue shirt in stock?”, it sends an A2A SendMessage call to a specialist Inventory Agent’s /.well-known/agent-card.json endpoint.
  • The Inventory Agent uses an MCP server connected to the company’s Shopify or Magento backend. It calls tools/call with the get_stock_level tool and returns the answer.
  • When the user asks to return an item, the Chatbot Agent uses A2A to delegate to a Returns Agent.
  • The Returns Agent uses MCP to interact with the order-management system, calling tools to create a return authorization and generate a shipping label.

This layered approach lets the Chatbot Agent focus on natural-language understanding while specialist agents handle the messy backend integrations behind a simple, dynamic-discovery interface.

Securing and operating agent protocols in production

An autonomous agent with access to tools and other agents presents a new attack surface. Deploying agentic systems in production requires treating every A2A and MCP interaction as a managed API call that must be authenticated, authorized, and observed.

Common security threats: A checklist for developers

ThreatDescriptionMitigation
Tool poisoning (MCP)A compromised MCP server returns malicious tool output that the agent then propagatesValidate tool outputs against the server-advertised outputSchema and treat all tool data as untrusted before passing back to the LLM
Agent Card poisoning (A2A)A malicious actor rewrites an Agent Card’s description/skills to embed prompt injectionRequire AgentCardSignature (JWS, RFC 7515) over a JCS-canonicalized card and reject unsigned or invalidly-signed cards from public agents
Prompt injectionMalicious user input is concatenated into an A2A message and sent to a downstream agentStrict input validation; LLM firewall at the gateway; clearly delimited system vs user content in meta-prompts
Excessive agencyAn agent has more permissions than it needs; a compromise yields a large blast radiusApply least privilege: A2A’s security field maps OAuth scopes to specific skills[]; use RFC 8693 Token Exchange to downscope before delegating
Webhook spoofing/SSRFPush-notification webhook URL points at internal IP, or attacker forges “task complete” payloadsAllow-list outbound destinations; enforce PushNotificationConfig.authentication on every notification (signed JWT/HMAC/mTLS)

On the A2A side, the spec’s central mitigation against Agent Card tampering is AgentCardSignature: cards SHOULD be signed using JWS (RFC 7515) over a JCS-canonicalized (RFC 8785) representation, and clients verify the signature against the issuer’s public key before trusting the card. Combine that with skill-scoped OAuth (security: [{ “corporate_oauth”: [“flights:write”] }]) and you have both authenticity and authorization pinned to the spec’s primitives.

On the MCP side, the 2025-11-25 Authorization spec defines OAuth 2.1 flows for remote MCP servers, and the Streamable HTTP transport explicitly requires Origin-header validation and binding to localhost for local servers to defend against DNS rebinding.

Monitoring and debugging: From black box to glass box

Agentic workflows are distributed, asynchronous, and non-deterministic. Effective observability requires the right approach for each protocol.

  • Debugging MCP: Sessions are short and call patterns are tight (initialize → tools/list → tools/call). Use an API management platform to inspect JSON-RPC payloads, monitor latency and error rates on tools/call endpoints, and watch for clients that don’t honour initialize/initialized.
  • Debugging A2A: Workflows can stretch across many agents and minutes-to-hours timeframes. Use OpenTelemetry with W3C Trace Context (traceparent/tracestate) headers on every A2A call. A2A’s enterprise-readiness page explicitly recommends this. Log taskId, contextId, and the authenticated agent identity (sub claim) on both sides. The Task state machine itself is a built-in observability tool; track transitions between SUBMITTED → WORKING → COMPLETED/FAILED/CANCELED/REJECTED and surface stuck Tasks as alerts.

Frequently asked questions

What is the main difference between MCP and A2A?

MCP standardizes how an AI application communicates with external tools, data sources, and workflows, typically via stdio for local servers or Streamable HTTP for remote ones. A2A standardizes how multiple independent agents collaborate and delegate tasks. MCP is for application-to-tool interaction; A2A is for agent-to-agent. The two protocols are complementary and frequently used together: An agent uses A2A externally to coordinate with peers and MCP internally to use its tools.

Is IBM’s ACP still relevant?

Not as a separate standard, no. In August 2025, IBM Research and Google announced that ACP would join forces with A2A under the Linux Foundation’s LF AI & Data umbrella. ACP development is winding down; its concepts (particularly its emphasis on stateful, long-running workflows) are being contributed to A2A. BeeAI users have a migration path via A2AServer/A2AAgent adapters and an official migration guide.

Do I need an API gateway for agent protocols?

Yes, an API gateway is critical in production. It provides centralized authentication (OAuth 2.0/OIDC validation, mTLS termination), authorization (skill-scoped policies), rate limiting, and observability for both A2A’s JSON-RPC endpoints and MCP’s Streamable HTTP endpoints. It lets you treat every agent interaction as a managed API call and centralizes policy enforcement rather than spreading it across agent code.

Can MCP and A2A be used together?

Yes, that’s the recommended pattern. A high-level orchestrator agent uses A2A to delegate complex tasks to specialist agents. Each specialist agent then uses MCP to interact with the specific tools, data sources, and workflows it needs. Concerns are cleanly separated: A2A handles coordination; MCP handles execution.

How do agent protocols handle authentication?

Both protocols specify authentication, contrary to a common misconception:

  • A2A declares accepted schemes in the AgentCard’s securitySchemes field (using the same shape as OpenAPI 3 SecurityScheme), and security maps schemes/scopes to specific skills. Supported schemes include API key, OAuth 2.0, OIDC, and mTLS. Credentials live in HTTP headers, never in the JSON-RPC payload.
  • MCP has a dedicated Authorization spec for remote servers that defines OAuth 2.1 flows. Local stdio servers are typically authorized by virtue of being launched by a trusted host process.

Conclusion

The agent-protocol landscape has consolidated around two complementary standards. The Model Context Protocol provides the universal interface for model-to-tool communication, and the unified Agent2Agent protocol (now incorporating ACP’s stateful, asynchronous concepts) is the standard for agent collaboration. Both are open-source, both are JSON-RPC, and both are governed under the Linux Foundation.

The right architecture isn’t either/or. Modern agentic systems layer the two: A2A for high-level orchestration and MCP for low-level tool execution. Deploying these powerful systems in production demands robust security (signed Agent Cards, skill-scoped OAuth, MCP Authorization for remote servers, mTLS or DPoP for sender-constrained tokens) and observability (OpenTelemetry with W3C Trace Context propagated across every hop). An API gateway becomes essential for managing access, monitoring traffic, and debugging distributed workflows.

As the LF AI & Data agent ecosystem matures, expect to see a rich set of compliant agents and tools emerge, with interoperability becoming a default rather than a custom integration project. To learn how to secure, control, and observe your agent communications at scale, explore how the Tyk MCP Gateway can manage your agent-protocol endpoints.

Share the Post:

Related Posts

Start for free

Get a demo

Ready to get started?

You can have your first API up and running in as little as 15 minutes. Just sign up for a Tyk Cloud account, select your free trial option and follow the guided setup.