> Discover all available pages from the documentation index: https://mastra.zisheng.pro/fr/llms.txt # A2A (Agent-to-Agent) Mastra prend en charge la version 0.3.0 du [protocole Agent-to-Agent (A2A)](https://a2a-protocol.org/latest/) pour les systèmes multi-Agents multiplateformes. Utilisez A2A pour exposer des Agents Mastra en tant qu'Agents distants, intégrer des Agents A2A distants comme sous-Agents Mastra ou appeler des endpoints A2A avec le SDK client JavaScript. A2A est un protocole ouvert permettant de déléguer des tâches à des Agents, indépendamment des réseaux, frameworks, fournisseurs et langages. Un Agent distant garde privés ses propres Tools, prompts, mémoire, Workflows et infrastructure, tout en exposant un endpoint de protocole que d'autres systèmes peuvent découvrir et appeler. ## Quand utiliser A2A - Un Agent parent doit déléguer une tâche à un Agent distant spécialisé. - Un Agent distant appartient à un autre service, une autre équipe, un autre fournisseur ou un autre environnement d'exécution. - Un backend, une application de navigateur ou un autre système compatible A2A doit accéder par programmation à un Agent Mastra. - Une tâche distante de longue durée nécessite des ID de tâche, des mises à jour d'état, des artefacts, une annulation, une réinscription ou des notifications push. ## Fonctionnement d'A2A A2A utilise une fiche d'Agent pour la découverte. Cette fiche est un document JSON servi depuis une URL bien connue. Elle décrit l'Agent distant et comprend l'URL d'exécution qui accepte les requêtes A2A JSON-RPC. Lorsque vous utilisez la valeur `apiPrefix` par défaut `/api` de Mastra Server, un Agent enregistré sous le nom `weather-agent` expose : - Fiche d'Agent : `/api/.well-known/weather-agent/agent-card.json` - Endpoint d'exécution : `/api/a2a/weather-agent` Une fiche d'Agent comprend notamment le nom et la description de l'Agent, l'URL de l'endpoint, le Provider, les fonctionnalités, les métadonnées de sécurité et les Skills : ```json { "protocolVersion": "0.3.0", "name": "Weather Agent", "description": "Provides weather information.", "url": "https://agent.example.com/api/a2a/weather-agent", "version": "1.0", "provider": { "organization": "Acme", "url": "https://acme.example.com" }, "capabilities": { "streaming": true, "pushNotifications": true, "stateTransitionHistory": false }, "defaultInputModes": ["text/plain"], "defaultOutputModes": ["text/plain"], "skills": [ { "id": "weather", "name": "weather", "description": "Gets weather conditions for a location.", "tags": ["tool"] } ] } ``` A2A représente le travail sous forme de messages et de tâches. Les messages transportent des parties de texte, de fichier ou de données structurées. Les tâches sont des unités de travail avec état, dotées d'ID et d'états de cycle de vie. Les clients peuvent suivre les tâches de longue durée et envoyer des échanges complémentaires. Ils peuvent également annuler une tâche ou se réinscrire après une déconnexion. ## Versions du protocole Mastra prend en charge les versions v0.3 et v1.0 du protocole A2A sur les mêmes URL de fiche d'Agent et d'exécution. L'en-tête de requête `A2A-Version` sélectionne le protocole utilisé sur le réseau : - Absent, vide ou égal à `0.3` : utilise l'API v0.3 existante. - `1.0` : utilise l'API v1.0. - Toute autre valeur : renvoie une erreur de protocole `VersionNotSupported`. Les intégrations `A2AAgent` et `MastraClient.getA2A()` existantes continuent d'utiliser la v0.3. Utilisez `MastraClient.getA2AV1()` pour les requêtes v1.0. Le client v1 envoie automatiquement `A2A-Version: 1.0` et ajoute l'opération `tasks/list`. Importez les types et codecs du protocole v1.0 depuis `@mastra/core/a2a/v1`. L'exportation `@mastra/core/a2a/client` existante reste en v0.3. ## Prise en main A2A s'utilise principalement de deux manières dans Mastra : - Intégrer un Agent A2A distant comme sous-Agent Mastra avec `A2AAgent`. - Envoyer des requêtes à un endpoint A2A Mastra avec `MastraClient.getA2A()`. Utilisez `A2AAgent` lorsqu'un autre Agent Mastra doit déléguer une tâche à un Agent distant. Utilisez le SDK client lorsque le code de l'application doit appeler directement un endpoint Mastra compatible A2A. ## Intégrer des Agents A2A comme sous-Agents Utilisez `A2AAgent` pour envelopper un Agent A2A distant, puis ajoutez-le à un Agent parent selon le modèle des [Agents superviseurs](https://mastra.zisheng.pro/fr/docs/capabilities/subagents). Transmettez explicitement l'URL de la fiche d'Agent lorsque le serveur distant héberge plusieurs Agents ou utilise un chemin bien connu personnalisé. ```typescript import { Agent } from '@mastra/core/agent' import { A2AAgent } from '@mastra/core/a2a' const remoteWeatherAgent = new A2AAgent({ url: 'https://weather.example.com/api/.well-known/weather-agent/agent-card.json', headers: { Authorization: `Bearer ${process.env.WEATHER_AGENT_TOKEN}`, }, }) export const supportAgent = new Agent({ id: 'support-agent', name: 'Support Agent', instructions: 'Answer user questions and delegate weather questions when needed.', model: 'openai/gpt-5.6-sol', agents: { remoteWeatherAgent, }, }) ``` Si `url` pointe vers un domaine, `A2AAgent` récupère la fiche d'Agent depuis `/.well-known/agent-card.json`. Utilisez une URL de domaine pour les serveurs à Agent unique qui suivent ce chemin de découverte. Pour les serveurs multi-Agents, transmettez l'URL complète de la fiche, par exemple `https://agent.example.com/api/.well-known/weather-agent/agent-card.json`. Pendant l'exécution, `A2AAgent` : - Récupère et met en cache la fiche de l'Agent distant. - Lit dans la fiche l'URL d'exécution et les fonctionnalités. - Appelle `message/send` pour les exécutions sans diffusion en continu ou `message/stream` lorsque celle-ci est prise en charge. - Convertit les messages, tâches, artefacts et mises à jour d'état distants en résultats de sous-Agent Mastra. - Prend en charge `resumeGenerate()` et `resumeStream()` lorsque la tâche distante nécessite une entrée complémentaire ou une réinscription. Si la fiche distante n'annonce pas la prise en charge de la diffusion en continu, `A2AAgent.stream()` se rabat sur le parcours de génération sans streaming et renvoie un résultat de flux mis en mémoire tampon. ## Envoyer des requêtes avec le SDK client Utilisez `MastraClient.getA2A()` lorsque le code de l'application doit appeler un Agent Mastra compatible A2A. Configurez `baseUrl` avec l'origine du serveur et `apiPrefix` lorsque le serveur n'utilise pas le préfixe `/api` par défaut. ```typescript import { MastraClient } from '@mastra/client-js' const client = new MastraClient({ baseUrl: 'https://agent.example.com', headers: { Authorization: `Bearer ${process.env.AGENT_API_TOKEN}`, }, }) const a2a = client.getA2A('weather-agent') const card = await a2a.getAgentCard() console.log(card.name, card.capabilities) ``` Utilisez `sendMessageStream()` pour envoyer un message et recevoir les mises à jour d'état de la tâche et des artefacts par Server-Sent Events (SSE) : ```typescript const stream = a2a.sendMessageStream({ message: { kind: 'message', role: 'user', messageId: crypto.randomUUID(), parts: [{ kind: 'text', text: "What's the weather in Prague?" }], }, }) for await (const event of stream) { if (event.kind === 'artifact-update') { console.log(event.artifact.parts) } } ``` Si un flux se déconnecte alors qu'une tâche est toujours en cours, utilisez `resubscribeTask()` pour recevoir les mises à jour en direct de cette tâche : ```typescript const updates = a2a.resubscribeTask({ id: 'task-123', }) for await (const event of updates) { console.log(event) } ``` ### Utiliser le client v1.0 Utilisez `getA2AV1()` pour adopter le protocole réseau A2A v1.0. Le package du protocole fournit des codecs permettant de créer des valeurs de requête v1 à partir d'entrées au format JSON : ```typescript import { ListTasksRequest } from '@mastra/core/a2a/v1' import { MastraClient } from '@mastra/client-js' const client = new MastraClient({ baseUrl: 'https://agent.example.com', }) const a2a = client.getA2AV1('weather-agent') const response = await a2a.listTasks( ListTasksRequest.fromJSON({ contextId: 'customer-support', pageSize: 20, }), ) for (const task of response.tasks) { console.log(task.id, task.status) } ``` Le client v1.0 prend en charge `getAgentCard()`, `sendMessage()`, `sendMessageStream()`, `getTask()`, `listTasks()`, `cancelTask()` et `resubscribeTask()`. ## Configurer les appels aux sous-Agents `A2AAgent` accepte des options de requête pour les environnements authentifiés ou soumis à des contraintes : ```typescript import { A2AAgent } from '@mastra/core/a2a' const remoteWeatherAgent = new A2AAgent({ url: 'https://weather.example.com/api/.well-known/weather-agent/agent-card.json', headers: { Authorization: `Bearer ${process.env.WEATHER_AGENT_TOKEN}`, }, retries: 2, backoffMs: 250, maxBackoffMs: 1000, timeoutMs: 30_000, }) ``` Vous pouvez également transmettre `credentials`, `fetch` et `abortSignal` lorsque l'environnement d'exécution nécessite un comportement de récupération personnalisé ou l'annulation des requêtes. ## Intervention humaine dans la boucle A2A représente les tâches avec intervention humaine (HITL) au moyen de l'état de tâche `input-required`. Lorsqu'une tâche s'interrompt pour attendre une entrée, le client fournit l'entrée manquante en envoyant un message complémentaire avec le même `taskId`, puis le serveur poursuit la tâche. Mastra associe son modèle de suspension des Agents à cet état dans les deux sens : - **En tant que serveur** : lorsqu'un Agent exposé est suspendu, la tâche passe à l'état `input-required`. Cela comprend les suspensions dues à [l'approbation d'un Tool](https://mastra.zisheng.pro/fr/docs/agents/agent-approval) ou à un Tool qui appelle `suspend()`. Le message d'état de la tâche comprend un prompt textuel et une partie de données avec les valeurs structurées `suspendPayload` et `resumeSchema`. Une requête `message/send` ou `message/stream` complémentaire avec le même `taskId` reprend l'exécution suspendue avec l'entrée fournie. - **En tant que client** : lorsqu'une tâche distante atteint l'état `input-required` ou `auth-required`, `A2AAgent` renvoie un résultat suspendu avec `finishReason: 'suspended'` et un `suspendPayload`. L'appel de `resumeGenerate()` ou `resumeStream()` renvoie l'entrée ou les identifiants à la tâche distante avec le `taskId` d'origine. ```typescript import { A2AAgent } from '@mastra/core/a2a' const agent = new A2AAgent({ url: 'https://agent.example.com/api/.well-known/booking-agent/agent-card.json', }) const result = await agent.generate('Book a flight to Paris', { runId: 'run-1' }) if (result.finishReason === 'suspended') { // Inspect result.suspendPayload, collect input from a human, // then resume the remote task. const resumed = await agent.resumeGenerate({ approved: true }, { runId: 'run-1' }) console.log(resumed.text) } ``` Les messages complémentaires d'une tâche `input-required` peuvent transporter les données de reprise dans une partie de données structurées, ou sous forme de JSON ou de texte brut dans une partie textuelle. Lorsqu'une exécution reprise nécessite une entrée supplémentaire, la tâche revient à l'état `input-required` et le processus se répète. La reprise d'une exécution suspendue nécessite la configuration d'un stockage sur le serveur Mastra afin que son état puisse être restauré d'une requête à l'autre. > **Remarque:** Les enregistrements de tâches A2A résident dans un stockage en mémoire. Une tâche mise en pause ne peut donc être reprise que par le processus serveur qui l'a suspendue. Un redémarrage du serveur ou un déploiement avec mise à l'échelle horizontale sans routage persistant perd l'enregistrement de la tâche, et tout message complémentaire échoue avec une erreur indiquant que la tâche est introuvable. ## Notifications push Mastra prend en charge les notifications push A2A pour les Agents distants qui annoncent `capabilities.pushNotifications`. Utilisez-les lorsqu'un client ne peut pas maintenir un flux ouvert ou lorsqu'une tâche de longue durée doit mettre à jour une URL de rappel après la fin de la requête d'origine. Une fois qu'un client dispose d'un ID de tâche, il peut enregistrer une URL de rappel pour celle-ci : ```typescript await a2a.setTaskPushNotificationConfig({ taskId: 'task-123', pushNotificationConfig: { url: 'https://app.example.com/a2a/tasks', token: process.env.A2A_WEBHOOK_TOKEN, }, }) ``` Mastra Server envoie l'instantané actuel de la tâche aux fonctions de rappel enregistrées lorsque la tâche atteint l'état `completed`, `failed`, `canceled`, `rejected`, `input-required` ou `auth-required`. L'envoi des notifications push est effectué au mieux. Protégez les URL de rappel, validez les tokens de notification et évitez d'exposer des cibles du réseau interne comme destinations de notifications push. Les configurations de notifications push sont stockées en mémoire et doivent être réenregistrées après un redémarrage du serveur. ## Signer et vérifier les fiches d'Agent Mastra prend en charge les fiches d'Agent A2A signées afin que les clients puissent vérifier qu'une fiche découverte provient d'un éditeur de confiance et n'a pas été modifiée pendant son transfert. Configurez la signature sur le serveur Mastra qui expose l'Agent distant : ```typescript import { Mastra } from '@mastra/core/mastra' export const mastra = new Mastra({ server: { a2a: { agentCardSigning: { privateKey: process.env.A2A_AGENT_CARD_PRIVATE_KEY!, protectedHeader: { alg: 'ES256', kid: 'agent-card-key', }, }, }, }, }) ``` Lorsque la signature est configurée, Mastra inclut un tableau `signatures` dans la fiche d'Agent. La vérification côté client doit être activée explicitement, et les fiches non signées sont toujours renvoyées sans modification. Vérifiez une fiche signée avec `MastraClient.getA2A()` : ```typescript const card = await a2a.getAgentCard({ verifySignature: { algorithms: ['ES256'], keyProvider: async ({ kid, jku }) => { return fetchTrustedPublicJwk({ kid, jku }) }, }, }) if (!card.signatures?.length) { throw new Error('Expected a signed A2A agent card.') } ``` Utilisez la vérification de signature côté client lorsque celui-ci doit imposer l'emploi de clés de confiance avant d'appeler l'Agent distant. ## Vérifier les fiches des sous-Agents Utilisez `verifyAgentCard` lorsqu'un Agent parent doit valider un Agent distant avant de lui déléguer une tâche. Le hook de vérification reçoit la fiche d'Agent récupérée ainsi que le contexte indiquant où et quand elle l'a été. ```typescript import { A2AAgent } from '@mastra/core/a2a' const remoteWeatherAgent = new A2AAgent({ url: 'https://weather.example.com/api/.well-known/weather-agent/agent-card.json', verifyAgentCard: { verify: async (card, context) => { if (card.provider?.organization !== 'Weather Inc') { throw new Error(`Unexpected provider for ${context.cardUrl}`) } }, }, }) ``` Utilisez ce hook pour imposer les Providers et endpoints attendus, les identités liées à un certificat, les fiches signées ou d'autres exigences de confiance avant qu'un Agent parent ne délègue une tâche à l'Agent distant. ## Voir aussi - [Référence des Agents](https://mastra.zisheng.pro/fr/reference/agents/agent) - [Référence des Agents du client JavaScript](https://mastra.zisheng.pro/fr/reference/client-js/agents) - [Concepts fondamentaux d'A2A](https://a2a-protocol.org/latest/topics/key-concepts/) - [Guide de découverte A2A](https://a2a-protocol.org/latest/topics/agent-discovery/) - 📹 [Atelier Agent-to-Agent avec Mastra](https://www.youtube.com/watch?v=LQDzyNGm-aw)