Déployer des serveurs A2A dans Runtime AgentCore
Amazon Bedrock AgentCore AgentCore Runtime vous permet de déployer et d'exécuter des serveurs Agent-to-Agent (A2A) dans le AgentCore Runtime. Ce guide vous explique comment créer, tester et déployer votre premier serveur A2A.
Dans cette section, vous allez apprendre :
-
Comment Amazon Bedrock AgentCore prend en charge l'A2A
-
Comment créer un serveur A2A doté de fonctionnalités d'agent
-
Comment tester votre serveur en local
-
Comment déployer votre serveur sur AWS
-
Comment appeler votre serveur déployé
-
Comment récupérer des cartes d'agent à des fins de découverte
Pour plus d'informations sur l'A2A, consultez le contrat de protocole A2A.
Rubriques
Comment Amazon Bedrock AgentCore prend en charge l'A2A
La prise en charge AgentCore du protocole A2A d'Amazon Bedrock permet une intégration parfaite avec les serveurs A2A en agissant comme une couche proxy transparente. Lorsqu'ils sont configurés pour A2A, Amazon Bedrock AgentCore s'attend à ce que les conteneurs exécutent des serveurs HTTP apatrides et streamables sur le port situé sur le chemin racine (0.0.0.0:9000/), ce qui correspond 9000 à la configuration du serveur A2A par défaut.
Le service permet d'isoler les sessions de niveau professionnel tout en préservant la transparence du protocole : les JSON-RPC charges utiles de l'InvokeAgentRuntimeAPI sont transmises directement au conteneur A2A sans modification. Cette architecture préserve les fonctionnalités standard du protocole A2A, telles que la découverte intégrée des agents par le biais de cartes d'agent /.well-known/agent-card.json et de JSON-RPC communication, tout en ajoutant l'authentification d'entreprise (SigV4/OAuth 2.0) et l'évolutivité.
Les principaux facteurs de différenciation par rapport aux autres protocoles sont le port (9000 contre 8080 pour HTTP), le chemin de montage (/vs/invocations) et le mécanisme standardisé de découverte des agents, faisant d'Amazon Bedrock AgentCore une plate-forme de déploiement idéale pour les agents A2A dans les environnements de production.
Principales différences par rapport aux autres protocoles :
- Port
-
Les serveurs A2A fonctionnent sur le port 9000 (contre 8080 pour HTTP, 8000 pour MCP)
- Chemin
-
Les serveurs A2A sont montés sur
/(contre HTTP,/invocations/mcppour MCP) - Cartes d'agent
-
L'A2A fournit une fonction intégrée de découverte des agents via des cartes d'agent sur
/.well-known/agent-card.json - Protocole
-
Utilisations JSON-RPC de la communication agent-agent
- Authentification
-
Supporte les schémas d'authentification Sigv4 et OAuth 2.0
Pour de plus amples informations, veuillez consulter https://a2a-protocol.org/
Utilisation d'A2A avec Runtime AgentCore
Dans ce didacticiel, vous allez créer, tester et déployer un serveur A2A.
Rubriques
Conditions préalables
-
Python 3.10 ou supérieur installé et compréhension de base de Python
-
Node.js 18 ou version supérieure installée (obligatoire pour la AgentCore CLI)
-
La AgentCore CLI installée :
npm install -g @aws/agentcore -
Un AWS compte avec les autorisations appropriées et les informations d'identification locales configurées
-
Compréhension du protocole A2A et des concepts de communication agent-agent
Étape 1 : Créez votre projet A2A
Cet exemple utilise des agents Strands, mais la AgentCore CLI prend également en charge les projets A2A avec LangChain/LangGraph Google ADK.
Échafaudage du projet
Exécutez la commande suivante et sélectionnez Strands comme framework lorsque vous y êtes invité :
agentcore create --protocol A2A
La CLI échafaude un projet complet avec toutes les dépendances et configurations requises. Le fichier généré main.py contient votre serveur A2A :
from strands import Agent, tool from strands.multiagent.a2a.executor import StrandsA2AExecutor from bedrock_agentcore.runtime import serve_a2a from model.load import load_model @tool def add_numbers(a: int, b: int) -> int: """Return the sum of two numbers.""" return a + b tools = [add_numbers] agent = Agent( model=load_model(), system_prompt="You are a helpful assistant. Use tools when appropriate.", tools=tools, ) if __name__ == "__main__": serve_a2a(StrandsA2AExecutor(agent))
Comprendre le code
- Agent Strands
-
Crée un agent doté d'outils et de capacités spécifiques
- Exécuteur Strands A2a
-
Enveloppe l'agent Strands pour assurer la compatibilité du protocole A2A
- serve_a2a
-
L'assistant du AgentCore SDK Amazon Bedrock qui démarre un Bedrock-compatible serveur A2A. Il gère le point de terminaison de
/pingsanté, le service de carte agent, la variable d'AGENTCORE_RUNTIME_URLenvironnement, la propagation de l'en-tête Bedrock et s'exécute sur le port 9000 par défaut. - Port 9000
-
Les serveurs A2A s'exécutent sur le port 9000 par défaut dans Runtime AgentCore
Pour personnaliser cet agent, remplacez l'add_numbersoutil par vos propres outils et mettez à jour l'invite du système.
Étape 2 : Testez votre serveur A2A localement
Exécutez et testez votre serveur A2A dans un environnement de développement local.
Démarrez votre serveur A2A
Démarrez votre serveur A2A localement à l'aide de la AgentCore CLI :
agentcore dev
L'inspecteur des AgentCore agents s'ouvre alors dans votre navigateur Web. Pour utiliser le TUI basé sur un terminal à la place, utilisez. agentcore dev --no-browser
Vous pouvez également exécuter le serveur directement :
python main.py
Vous devriez voir une sortie indiquant que le serveur fonctionne sur le port9000.
Invoquer l'agent
curl -X POST http://localhost:9000/ \ -H "Content-Type: application/json" \ -d '{ "jsonrpc": "2.0", "id": "req-001", "method": "message/send", "params": { "message": { "role": "user", "parts": [ { "kind": "text", "text": "what is 101 * 11?" } ], "messageId": "12345678-1234-1234-1234-123456789012" } } }' | jq .
Récupération de la carte d'agent de test
Vous pouvez tester le point de terminaison de la carte agent localement :
curl http://localhost:9000/.well-known/agent-card.json | jq.
Vous pouvez également tester votre serveur déployé à l'aide de l'inspecteur A2A, comme décrit dans Tests à distance avec l'inspecteur A2A
Étape 3 : Déployez votre serveur A2A sur Bedrock Runtime AgentCore
Configuration du groupe d'utilisateurs Cognito pour l'authentification
Avant le déploiement, configurez l'authentification pour un accès sécurisé à votre serveur déployé. Pour obtenir des instructions détaillées sur la configuration de Cognito, voir Configurer le groupe d'utilisateurs de Cognito pour l'authentification. Cela fournit les jetons OAuth nécessaires pour un accès sécurisé à votre serveur déployé.
Déployer vers AWS
Déployez votre agent :
agentcore deploy
Cette commande permettra de :
-
Package du code de votre agent et de ses dépendances
-
Téléchargez l'artefact de déploiement sur Amazon S3
-
Création d'un environnement d'exécution Amazon Bedrock AgentCore
-
Déployez votre agent sur AWS
Après le déploiement, vous recevrez un ARN d'exécution de l'agent qui ressemble à ce qui suit :
arn:aws:bedrock-agentcore:us-west-2:accountId:runtime/my_a2a_server-xyz123
Étape 4 : Obtenir la carte d'agent
Les cartes d'agent sont des documents de métadonnées JSON qui décrivent l'identité, les capacités, les compétences, le point de terminaison du service et les exigences d'authentification d'un serveur A2A. Ils permettent la découverte automatique des agents dans l'écosystème A2A.
Configurer les variables d’environnement
Configurer les variables d’environnement
-
Exportez le jeton porteur en tant que variable d'environnement. Pour la configuration du jeton porteur, voir Configuration du jeton porteur.
export BEARER_TOKEN="<BEARER_TOKEN>" -
Exportez l'ARN de l'agent.
export AGENT_ARN="arn:aws:bedrock-agentcore:us-west-2:accountId:runtime/my_a2a_server-xyz123"
Récupérez la carte d'agent
import os import json import requests from uuid import uuid4 from urllib.parse import quote def fetch_agent_card(): # Get environment variables agent_arn = os.environ.get('AGENT_ARN') bearer_token = os.environ.get('BEARER_TOKEN') if not agent_arn: print("Error: AGENT_ARN environment variable not set") return if not bearer_token: print("Error: BEARER_TOKEN environment variable not set") return # URL encode the agent ARN escaped_agent_arn = quote(agent_arn, safe='') # Construct the URL url = f"https://bedrock-agentcore.us-west-2.amazonaws.com/runtimes/{escaped_agent_arn}/invocations/.well-known/agent-card.json" # Generate a unique session ID session_id = str(uuid4()) print(f"Generated session ID: {session_id}") # Set headers headers = { 'Accept': '*/*', 'Authorization': f'Bearer {bearer_token}', 'X-Amzn-Bedrock-AgentCore-Runtime-Session-Id': session_id } try: # Make the request response = requests.get(url, headers=headers) response.raise_for_status() # Parse and pretty print JSON agent_card = response.json() print(json.dumps(agent_card, indent=2)) return agent_card except requests.exceptions.RequestException as e: print(f"Error fetching agent card: {e}") return None if __name__ == "__main__": fetch_agent_card()
Une fois que vous avez obtenu l'URL depuis la carte d'agent, exportez-la AGENTCORE_RUNTIME_URL en tant que variable d'environnement :
export AGENTCORE_RUNTIME_URL="https://bedrock-agentcore.us-west-2.amazonaws.com/runtimes/<ARN>/invocations/"
Étape 5 : Invoquez votre serveur A2A déployé
Créez un code client pour appeler votre serveur Amazon Bedrock AgentCore A2A déployé et envoyez des messages pour tester les fonctionnalités.
Créez un nouveau fichier my_a2a_client_remote.py pour appeler votre serveur A2A déployé :
import asyncio import logging import os from uuid import uuid4 import httpx from a2a.client import A2ACardResolver, ClientConfig, ClientFactory from a2a.types import Message, Part, Role, TextPart logging.basicConfig(level=logging.INFO) logger = logging.getLogger(__name__) DEFAULT_TIMEOUT = 300 # set request timeout to 5 minutes def create_message(*, role: Role = Role.user, text: str) -> Message: return Message( kind="message", role=role, parts=[Part(TextPart(kind="text", text=text))], message_id=uuid4().hex, ) async def send_sync_message(message: str): # Get runtime URL from environment variable runtime_url = os.environ.get('AGENTCORE_RUNTIME_URL') # Generate a unique session ID session_id = str(uuid4()) print(f"Generated session ID: {session_id}") # Add authentication headers for Amazon Bedrock AgentCore headers = {"Authorization": f"Bearer {os.environ.get('BEARER_TOKEN')}", 'X-Amzn-Bedrock-AgentCore-Runtime-Session-Id': session_id} async with httpx.AsyncClient(timeout=DEFAULT_TIMEOUT, headers=headers) as httpx_client: # Get agent card from the runtime URL resolver = A2ACardResolver(httpx_client=httpx_client, base_url=runtime_url) agent_card = await resolver.get_agent_card() # Agent card contains the correct URL (same as runtime_url in this case) # No manual override needed - this is the path-based mounting pattern # Create client using factory config = ClientConfig( httpx_client=httpx_client, streaming=False, # Use non-streaming mode for sync response ) factory = ClientFactory(config) client = factory.create(agent_card) # Create and send message msg = create_message(text=message) # With streaming=False, this will yield exactly one result async for event in client.send_message(msg): if isinstance(event, Message): logger.info(event.model_dump_json(exclude_none=True, indent=2)) return event elif isinstance(event, tuple) and len(event) == 2: # (Task, UpdateEvent) tuple task, update_event = event logger.info(f"Task: {task.model_dump_json(exclude_none=True, indent=2)}") if update_event: logger.info(f"Update: {update_event.model_dump_json(exclude_none=True, indent=2)}") return task else: # Fallback for other response types logger.info(f"Response: {str(event)}") return event # Usage - Uses AGENTCORE_RUNTIME_URL environment variable asyncio.run(send_sync_message("what is 101 * 11"))
Annexe
Rubriques
Configuration du groupe d'utilisateurs Cognito pour l'authentification
Pour obtenir des instructions détaillées sur la configuration de Cognito, consultez la section Configurer le groupe d'utilisateurs Cognito pour l'authentification dans la documentation MCP.
Tests à distance avec l'inspecteur A2A
Consultez https://github.com/a2aproject/a2a-inspector
Résolution des problèmes
A2A-specific Problèmes courants
Les problèmes courants que vous pouvez rencontrer sont les suivants :
- Conflits portuaires
-
Les serveurs A2A doivent fonctionner sur le port 9000 dans l' AgentCore environnement d'exécution
- JSON-RPC erreurs
-
Vérifiez que votre client envoie des messages JSON-RPC 2.0 correctement formatés
- Incompatibilité entre les méthodes d'autorisation
-
Assurez-vous que votre demande utilise la même méthode d'authentification (OAuth ou Sigv4) que celle avec laquelle l'agent a été configuré
Gestion des exceptions
Spécifications A2A pour la gestion des erreurs : https://a2a-protocol.org/latest/specification/#81-standard-json-rpc-errors
Les serveurs A2A renvoient les erreurs sous forme de réponses JSON-RPC d'erreur standard avec des codes d'état HTTP 200. Les erreurs d'exécution internes sont automatiquement converties en erreurs JSON-RPC internes afin de garantir la conformité au protocole.
Le service fournit désormais des réponses aux A2A-compliant erreurs appropriées avec des codes JSON-RPC d'erreur standardisés :
| JSON-RPC Code d'erreur | Exception d'exécution | Code d'erreur HTTP | JSON-RPC Message d'erreur |
|---|---|---|---|
|
N/A |
|
403 |
N/A |
|
-32501 |
|
404 |
Ressource introuvable — La ressource demandée n'existe pas |
|
-32502 |
|
400 |
Erreur de validation — Données de demande non valides |
|
-32503 |
|
429 |
Limite de débit dépassée — Trop de demandes |
|
-32503 |
|
429 |
Limite de débit dépassée — Trop de demandes |
|
-32504 |
|
409 |
Conflit de ressources — La ressource existe déjà |
|
-32505 |
|
424 |
Erreur du client d'exécution : consultez vos CloudWatch journaux pour plus d'informations. |