Tutoriel
Comment un agent IA en trouve-t-il un autre ? Agent Registry, A2A Agent Card et découverte de capacités JSON
Quand la découverte échoue, nommez d’abord le saut : recherche catalogue, récupération de carte, ou un domaine déjà en main avec le mauvais GET.
Le billet précédent, le tutoriel des champs Agent Card, a ouvert la table obligatoire 1.0. Aujourd’hui on ne re-remplit pas les champs, et on ne refait pas pourquoi un Registry est un catalogue. La question suivante de l’orchestrateur : comment passer de « j’ai besoin d’un collègue qui classe les retours » à une Card appelable ? La réponse officielle est sur A2A Agent Discovery : trois stratégies, une Card. La spécification ne définit pas d’API de requête pour un catalogue curaté — voir Considerations sur la même page. Le catalogue Google Cloud est une implémentation ; caler la forme sur les Registry JSON schemas. Ce texte suit les sauts. Délégation latérale contre appel d’outils vers le bas : A2A vs MCP. On ne reprend pas la couche.
La découverte n’est pas un protocole. On trouve une Card
A2A normalise une auto-description, pas un annuaire. L’agent distant écrit ses capacités en carte JSON. Le client s’en sert pour juger l’adéquation, le branchement, la Task à envoyer. La méthode change avec l’environnement : Internet public, catalogue d’entreprise, URL figée sur un portable. Les trois peuvent aboutir à la même Card. Appeler « découverte » un autre protocole de conversation, et la revue part de travers. Le protocole reste A2A. Ce qui change, c’est la porte vers well-known ou vers un catalogue.
La page officielle de découverte parle encore, dans « Role of the Agent Card », d’une url de premier niveau — c’est le langage 0.3. Les cartes neuves suivent 1.0 : le point d’entrée est dans supportedInterfaces. Voir les nouveautés de la v1.0. Si un saut lit encore l’ancien champ, ce n’est pas le contrat 1.0. Comment écrire les champs : le billet précédent. Aujourd’hui seulement : quel saut a mis cette carte dans votre main, et quelles clés vérifier d’abord.
Un find réussi n’autorise pas tools/call. En face, l’agent reste opaque. Vous choisissez un skill, une interface, vous envoyez une Task. Traiter un hit de recherche comme une table de fonctions, et les tours de clarification feront exploser arguments. Comment un saut MCP vérifie les paramètres : le texte Schema du site. On s’arrête à « qui avons-nous trouvé, et pourquoi croire qu’il traite ça ».
| Stratégie | Ce que vous savez déjà | Saut suivant |
|---|---|---|
| URI well-known | Un domaine ou un hôte | GET /.well-known/agent-card.json |
| Catalogue curaté | Mots-clés / tags de skill | Interroger le catalogue, puis récupérer la Card ou un pointeur |
| Configuration directe | Une URL ou la carte entière | Sauter la recherche, lire la carte |
Trois stratégies officielles : choisir la route, puis marcher
Well-known convient à un agent public, ou à une découverte quand vous tenez le nom d’hôte. Le chemin suit RFC 8615 : https://{agent-server-domain}/.well-known/agent-card.json. Le client connaît le domaine ou peut le déduire, envoie un GET HTTP, reçoit du JSON. L’implémentation est simple, facile à automatiser. Si la carte contient des skills sensibles ou une URL interne, ce GET lui-même doit être authentifié. N’exposez pas un point d’entrée intranet sur l’Internet ouvert.
Un catalogue curaté convient à l’entreprise ou au marché : un service intermédiaire collecte des Cards, les clients interrogent par skills, tags, provider ou capabilities, le catalogue renvoie des cartes ou des pointeurs. Vous gagnez la gouvernance et la recherche par capacité. Vous devez aussi nourrir le catalogue. A2A ne spécifie pas cette API. Google Agent Registry, un registre communautaire et un catalogue maison inventent chacun leur forme de requête. Ne validez pas trois vendeurs contre un « discover JSON universel ».
La configuration directe convient à un couple serré, un agent privé, un portable. L’URL de la carte vit dans une variable d’environnement, un fichier ou une API propriétaire. Relation statique : c’est le chemin le moins cher. La Card bouge, chaque client doit bouger. En production, traiter « figé sur le portable » comme seule surface de découverte, c’est un carnet d’adresses 2025. Les trois routes peuvent coexister : le catalogue trouve qui, well-known lit encore la carte si le catalogue est à terre, la config sème un ou deux hôtes stables au démarrage.
Vous avez un nom d’hôte : GET well-known
Le saut le plus propre a trois pas. (1) Obtenir un domaine, par exemple returns.agents.example.com. (2) GET https://returns.agents.example.com/.well-known/agent-card.json. (3) La réponse est une Card qui passe le schéma 1.0. Mauvais chemin, alias interne à la place de HTTP, nom d’hôte du certificat qui ne colle pas : le ticket dira « découverte en échec ». La Card peut être saine. Le GET n’est jamais arrivé.
La spécification demande des en-têtes de cache sur le point d’entrée de la Card. Cache-Control: max-age=… évite aux intermédiaires et aux clients de tout retélécharger. ETag peut être la version ou un hash du contenu. Après expiration, une requête conditionnelle (If-None-Match), pas un GET inconditionnel. Si le serveur n’envoie pas d’en-têtes, le client peut poser un défaut court — mais il ne doit pas cacher pour toujours une carte dont les skills peuvent changer.
Une carte publique n’a besoin que de quoi permettre à un orchestrateur de choisir. Skills sensibles et second point d’entrée interne vont sur une carte étendue authentifiée. On récupère la seconde copie seulement si capabilities.extendedAgentCard est vrai. Un saut de découverte ne doit pas supposer cette carte avant authentification. Un catalogue qui renvoie des Cards différentes selon l’identité, et une carte well-known identique pour tous, sont deux modèles de divulgation. Deux phrases dans la revue.
Vous avez un catalogue : chercher les tags, puis la Card
Sans nom d’hôte, seulement la phrase « trouve quelqu’un qui classe les retours », vous marchez un catalogue curaté. La requête mange skills[].tags et les noms de skill sur la Card — pas la topologie de vos slides. Les orchestrateurs dans un projet Google, Gemini Enterprise et Agent Gateway cherchent les inscriptions par mots-clés de skill. C’est un comportement produit, pas un RPC standard A2A. Communauté et autres clouds ont chacun leur search. Une fixture de revue doit affirmer « requête → liste de hits → chaque ligne a un cardUrl ou une Card embarquée ». N’élevez pas le chemin d’un vendeur au rang de spécification.
Si le catalogue renvoie un pointeur, le saut suivant reste well-known ou l’URL de Card qu’il a donnée. S’il renvoie une Card embarquée, vous la validez quand même contre le schéma 1.0 : un enregistrement réussi n’est pas un jeu de champs légal. Une entrée NO_SPEC avec un hôte et sans skills a une surface de recherche vide — déjà dit en #5. Rappel du jour : un saut par mot-clé sur un index vide n’est pas un protocole cassé.
Un catalogue à terre n’arrête pas la découverte tout seul. Si vous tenez déjà un nom d’hôte, le client doit encore GET well-known. Traiter le catalogue comme unique vérité, c’est single-pointer la surface. Gardez un ou deux hôtes stables dans la config de semence, reprenez la recherche par mots-clés quand le catalogue revient. C’est plus proche des trois stratégies coexistantes de la spec que « catalogue 500, on s’arrête ».
Après le hit : aligner les skills, choisir l’interface, envoyer une Task
Un hit de recherche dit seulement « peut-être celui-là ». L’orchestrateur parcourt encore skills[] : id est-il le genre de travail à déléguer, les tags collent-ils vraiment à la requête, acceptez-vous la frontière de description ? N’enveloppez pas un skill dans un inputSchema MCP. Les indices 1.0 sont examples et les MIME. Mauvais skill puis Task : l’échec est à la délégation, pas à la découverte — mais la fixture doit écrire « hit ≠ sélection » en deux étapes.
Après la sélection, lire supportedInterfaces. La première entrée est préférée. Le client choisit une liaison qu’il parle : JSONRPC, GRPC, HTTP+JSON. Pas de liaison commune : découverte réussie, appel raté. Une url 0.3 de premier niveau n’est pas le point d’entrée 1.0. Lire aussi les drapeaux : streaming faux et vous souscrivez quand même un flux, la spec veut une erreur de capacité, pas un repli silencieux vers unary.
Le JSON ci-dessous est une fixture de parcours, pas l’API officielle d’un catalogue. Il plie requête, hit et interface préférée en un objet, pour le diff à côté de la Card du dépôt. Le verbe suivant est message/send. Listes de validation et signatures : un billet plus tard.
{
"kind": "discovery-trace",
"note": "CI/review fixture — not an official A2A or Google Registry API",
"query": {
"tags": ["returns", "classify"]
},
"strategy": "curated-registry",
"hits": [
{
"name": "Returns Specialist",
"cardUrl": "https://returns.agents.example.com/.well-known/agent-card.json",
"matchedTags": ["returns", "classify"],
"skillId": "classify-return"
}
],
"selected": {
"skillId": "classify-return",
"preferredInterface": {
"url": "https://agents.example.com/returns/a2a",
"protocolBinding": "JSONRPC",
"protocolVersion": "1.0"
},
"next": "message/send"
}
}
| Ce saut | Entrée | Ce qu’il faut affirmer |
|---|---|---|
| Chercher le catalogue | Tags ou nom de skill | Liste de hits non vide, avec un pointeur |
| Récupérer well-known | Nom d’hôte ou cardUrl | Le JSON parse ; il passe le schéma 1.0 |
| Sélectionner / choisir une interface | Card 1.0 complète | L’id de skill colle ; le client parle l’interface |
Cache, index périmés et fixtures
Les Cards bougent peu : un skill de plus, un changement d’auth. La surface de découverte vieillit quand même. L’index du catalogue retarde, well-known sert déjà une nouvelle version, la recherche pointe encore d’anciens tags. Au moins deux fixtures : un cliché du hit catalogue, et la Card tout juste GET. Mots-clés qui manquent : d’abord tags et retard d’index, ensuite seulement un client 1.0 qui aurait lu une carte 0.3.
{
"hop": "well-known",
"method": "GET",
"url": "https://returns.agents.example.com/.well-known/agent-card.json",
"requestHeaders": {
"If-None-Match": "1.0.3"
},
"response": {
"status": 304,
"etag": "1.0.3",
"cacheControl": "max-age=3600"
}
}
La spec est nette : les données sensibles exigent une authentification. Préférez des identifiants dynamiques hors bande. N’écrivez pas un secret statique dans la Card. Une fixture de découverte qui contient un jeton ou un mot de passe intranet échoue à vue. Écrivez la carte publique comme si on allait la tirer. Le cache de la carte étendue suit la session. Ne le versez pas dans le même seau que le max-age de la carte publique.
Un SKILL.md de Plugin ou un tools/list MCP n’est pas une source de découverte non plus. Comment un agent de code du même dépôt fait pousser des skills, c’est la boîte. Comment l’agent retours d’une autre équipe se trouve, c’est la Card. Les deux dans un même capability.json, et trois sauts ratés atterrissent sur la même ligne de ticket.
Dans le navigateur : Formater du JSON pour voir si la fixture et la Card parsent ; Valider un schéma JSON pour la Card 1.0 après un hit ; JSON Diff pour comparer le cliché catalogue et la Card fraîche, attraper la dérive tags / interface. Les données restent sur cette machine. Pour aller plus loin : le tutoriel des champs Agent Card, et le tour d’horizon Registry. Signatures et liste de validation : le prochain texte pratique.
Liens : A2A Agent Card JSON Schema, Google Agent Registry, A2A vs MCP.
FAQ
J’ai un catalogue : faut-il encore GET well-known ?
Oui. Le catalogue consomme des Cards, il ne les remplace pas. La spec écrit well-known comme chemin standard de la découverte publique. Catalogue à terre, un client qui tient encore un nom d’hôte doit lire la carte.
A2A définit-il un RPC standard « chercher des agents » ?
Non. La page de découverte est explicite : la spec actuelle ne prescrit pas d’API de catalogue curaté. Chaque catalogue définit sa requête. Ce qui est standard, c’est la forme de la Card et le chemin well-known.
Je les ai trouvés : puis-je tools/call ?
Non. Un hit est un résultat de découverte. En face, un agent opaque ; vous envoyez une Task. Les paramètres déterministes restent aux outils MCP. Ne les écrivez pas dans le saut de découverte.
Combien de temps cacher ?
D’abord Cache-Control et ETag du serveur. Sans en-têtes, un défaut court et des requêtes conditionnelles après expiration. Skills ou auth qui changent : version doit bouger. Un client ne doit pas router la production sur des tags périmés.
À retenir et la suite
En 2026, « trouver automatiquement un autre agent » se plie en trois sauts : choisir une stratégie, obtenir une Card, décider de déléguer d’après skills et interfaces. Un catalogue est une porte, pas le protocole.
Ordre de mise en prod : d’abord well-known correct pour un agent public ; besoin de mots-clés, brancher un catalogue vendeur et apporter votre fixture de requête ; après un hit, valider la Card 1.0 puis envoyer une Task. Écrire les champs : billet précédent. Qu’est-ce qu’un catalogue : #5. Validation et signatures plus tard. Diff de la JSON de parcours contre la Card du dépôt dans JSONVue.