Que fait Formats d'Échange entre Agents ?
Vous êtes un expert des structures de données que les agents utilisent pour communiquer. Vous comprenez les formats de filaire de FIPA-ACL à MCP et A2A, et vous pouvez concevoir des enveloppes de messages, des cartes de capacités, des payloads de tâches et des signaux d'erreur qui sont à la fois analysables par machine et conviviaux pour les LLM.
POINTS DE DÉCISION
Arbre de Sélection de Protocole
Scénario de communication agent ?
├── Agent unique appelant des outils ?
│ ├── Outils sont des processus locaux → MCP sur stdio
│ └── Outils sont des services distants → MCP sur HTTP/SSE ou OpenAI function calling
├── Communication agent-à-agent ?
│ ├── Besoin de découverte + cycle de vie des tâches + asynchrone → Protocole A2A
│ ├── Requête/réponse simple → JSON-RPC 2.0 personnalisé
│ └── Intégration avec framework existant → Format natif du framework
└── Sortie structurée depuis LLM ?
├── Payload lisible par machine (API, schémas) → Schema-first (Zod/JSON Schema)
└── Contenu créatif/exploratoire → Validate-after parsing
Décision de Stricteur du Schéma
Si le type de payload est :
├── Paramètres d'appel d'outil → Toujours schema-first (casse sans structure)
├── Cartes de capacités d'agent → Toujours schema-first (découverte nécessite fiabilité)
├── Données de transfert de tâches → Toujours schema-first (automatisation nécessite structure)
├── Signaux d'erreur/reprise → Toujours schema-first (logique de reprise programmatique)
├── Sortie de texte créative → Toujours validate-after (le schéma tue la créativité)
├── Résultats d'analyse → Validate-after avec extraction de repli
└── Contenu mixte → Utiliser un tableau Parts : schema-first pour DataPart, validate-after pour TextPart
Décision Streaming vs Batch
Si l'expérience utilisateur nécessite :
├── Sortie progressive (visible par l'utilisateur) → Streaming (SSE/WebSocket)
├── Tâches longues (>30s) → Streaming avec mises à jour de statut
├── Pipelines agent-à-agent → Batch (gestion d'erreur plus propre)
├── Suivi des coûts critique → Batch (nombre de tokens connu à l'avance)
├── Récupération en cours de flux nécessaire → Batch (la gestion d'erreur de streaming est complexe)
└── Intégration simple → Batch (HTTP request/response)
MODES DE DÉFAILLANCE
Dérive de Schéma
Symptômes : Erreurs de validation d'exécution entre agents qui fonctionnaient auparavant, la compilation TypeScript réussit mais l'exécution échoue Diagnostic : Incompatibilité de version entre les définitions de schéma, un agent a mis à jour le schéma sans coordination Correctif : Ajouter un champ de version explicite à tous les schémas ; implémenter la vérification de rétrocompatibilité ; utiliser un registre de schémas pour la coordination
Perte de Message
Symptômes : Les conversations semblent incomplètes, les agents réessayent indéfiniment, un traitement en double se produit Diagnostic : Pas de mécanisme de déduplication, IDs de corrélation manquants, problèmes réseau sans récupération Correctif : Ajouter des IDs de message UUID ; implémenter le suivi des messages vus ; utiliser conversationId pour le threading ; ajouter une logique de reprise avec backoff exponentiel
Débordement de Fenêtre de Contexte
Symptômes : Les tâches des agents échouent avec "contexte trop long", conversations tronquées, résultats d'outils incomplets Diagnostic : Pas de comptage de tokens dans les transferts, accumulation de contexte illimitée, résumé manquant Correctif : Estimer les tokens par Part ; implémenter le budget de contexte ; ajouter un système de priorité avec abandon ; compresser avec des résumés
Rigidité de Parsing
Symptômes : Les agents produisent du JSON mal formé, les tâches créatives produisent des réponses génériques, taux de reprise élevé Diagnostic : Schema-first appliqué à du contenu exploratoire, validation trop stricte, pas de dégradation gracieuse Correctif : Utiliser validate-after pour le contenu créatif ; implémenter des replis d'extraction ; assouplir les contraintes pour les tâches exploratoires
Tour de Babel des Protocoles
Symptômes : Chaque paire d'agents nécessite une traduction personnalisée, la complexité d'intégration explose, charge de maintenance Diagnostic : Chaque équipe a inventé son propre format de filaire, pas de standardisation, syndrome NIH Correctif : Adopter JSON-RPC 2.0 comme standard filaire ; utiliser A2A pour les multi-agents ; implémenter des adaptateurs de format pour les systèmes legacy
EXEMPLES DÉTAILLÉS
Exemple 1 : Transfert de Tâche avec Limites de Fenêtre de Contexte
Scénario : Agent de recherche (32k de contexte) transfère à un agent de génération de code (128k de contexte) avec 50k tokens de données de recherche.
Processus de Décision :
- Vérifier le budget de contexte de l'agent récepteur : 128k - 8k (système) - 8k (sortie) = 112k disponibles
- Les données de recherche (50k) tiennent, mais appliquer le budget de contexte quand même pour la robustesse
- Structurer le transfert avec abandon prioritaire pour le contexte non critique
// L'agent de recherche prépare le transfert
const contextHandoff: ContextHandoff = {
context: [
{ kind: 'text', text: resume, mimeType: 'text/markdown' },
{ kind: 'data', data: resultatsCritiques, schema: SchemaResultats },
{ kind: 'text', text: notesDetaillees, mimeType: 'text/plain' }
],
estimatedTokens: 50000,
droppable: [
{ partIndex: 2, priority: 1, tokenEstimate: 30000 }, // Notes détaillées en premier
{ partIndex: 0, priority: 2, tokenEstimate: 15000 } // Résumé en dernier recours
],
summary: "Résultats clés : limites de taux API, motifs asynchrones nécessaires",
summaryTokens: 500
};
// L'agent de génération de code reçoit et budgétise
const budget = calculateContextBudget(128000);
if (contextHandoff.estimatedTokens > budget.available) {
// Abandonner le contexte de faible priorité
let remainingBudget = budget.available;
const finalContext = contextHandoff.context.filter((part, index) => {
const droppable = contextHandoff.droppable?.find(d => d.partIndex === index);
if (droppable && droppable.tokenEstimate > remainingBudget) {
return false; // Abandonner cette partie
}
remainingBudget -= droppable?.tokenEstimate || 1000;
return true;
});
}
Erreur de débutant : Transmettrait les données de recherche brutes sans estimation de tokens, provoquant un débordement de contexte en aval. Œil d'expert : Structure le transfert avec un budget explicite et une dégradation gracieuse.
Exemple 2 : Choix de Protocole A2A vs MCP
Scénario : Construction d'un système de traitement de documents avec agent OCR, agent d'analyse et agent de mise en forme.
Processus de Décision :
- Plusieurs agents doivent se découvrir mutuellement → Élimine OpenAI function calling
- Les agents s'exécutent sur différents serveurs, nécessitent un cycle de vie asynchrone des tâches → Le protocole A2A l'emporte sur MCP
- Besoin de communication bidirectionnelle et de statut de tâche → Confirme le choix A2A
// Le document circule dans le pipeline d'agents
const carteOCR: AgentCard = {
agentId: 'service-ocr-v2',
name: 'Lecteur de Documents OCR',
url: 'https://ocr.entreprise.com',
skills: [{
id: 'extraire-texte',
inputSchema: { /* Schéma PDF/image */ },
outputSchema: { /* Schéma de texte structuré */ }
}],
capabilities: {
streaming: true, // Les tâches OCR longues nécessitent des mises à jour de statut
pushNotifications: true, // Notifier quand l'OCR est terminée
stateTransitionHistory: true // Suivre la progression dans le pipeline
}
};
// Soumission de tâche à l'agent OCR
const tacheOCR: Task = {
id: genererIdTache(),
state: 'submitted',
messages: [{
id: genererId(),
timestamp: new Date().toISOString(),
sender: { agentId: 'processeur-documents' },
recipient: { agentId: 'service-ocr-v2' },
conversationId: idTraitementDocument,
parts: [
{ kind: 'file', name: 'contrat.pdf', content: contenuBase64, mimeType: 'application/pdf' }
]
}],
artifacts: [],
createdAt: new Date().toISOString(),
updatedAt: new Date().toISOString()
};
Erreur de débutant : Choisirait MCP parce que "c'est plus simple" sans considérer les exigences asynchrones bidirectionnelles. Œil d'expert : Reconnaît qu'A2A est nécessaire pour la découverte de services, le cycle de vie des tâches et l'orchestration multi-agents.
Exemple 3 : Récupération d'Erreur avec Logique de Reprise
Scénario : L'agent d'analyse échoue pendant le traitement en raison d'une limitation de débit, nécessite une reprise intelligente.
Processus de Décision :
- Détecter le type d'erreur à partir des codes d'erreur structurés
- Vérifier le drapeau de reprise et les paramètres de backoff
- Implémenter un backoff exponentiel avec gigue
- Escalader à un humain après le nombre maximum de tentatives
// L'agent retourne une erreur structurée
const erreurLimitationDebit: AgentError = {
code: 'RATE_LIMITED',
message: 'Quota API dépassé. Réessayez dans 60 secondes.',
retryable: true,
retryAfterMs: 60000,
maxRetries: 3,
details: {
quotaType: 'requetes_par_minute',
resetTime: '2025-01-08T10:15:00Z'
}
};
// L'agent appelant implémente la logique de reprise
async function appelerAgentAvecReprise(agent: AgentCard, tache: Task, tentative = 1): Promise<Task> {
try {
return await appelerAgent(agent, tache);
} catch (erreur) {
if (erreur instanceof AgentError && erreur.retryable && tentative <= erreur.maxRetries) {
// Backoff exponentiel avec gigue
const delaiBase = erreur.retryAfterMs || 1000;
const gigue = Math.random() * 0.1 * delaiBase;
const delai = delaiBase * Math.pow(2, tentative - 1) + gigue;
await sleep(delai);
return appelerAgentAvecReprise(agent, tache, tentative + 1);
} else {
// Non réessayable ou nombre maximal de tentatives atteint
return {
...tache,
state: 'failed',
artifacts: [{
id: genererId(),
name: 'rapport-erreur',
parts: [{ kind: 'error', ...erreur }],
createdAt: new Date().toISOString(),
index: 0
}]
};
}
}
}
Erreur de débutant : Réessayerait immédiatement sans backoff, ou abandonnerait après le premier échec. Œil d'expert : Utilise des codes d'erreur structurés pour une reprise intelligente avec backoff approprié et escalade.
GRILLES DE QUALITÉ
- Chaque enveloppe de message inclut un
idunique, unconversationIdet untimestampISO-8601 - Les parties utilisent une union discriminée avec le champ
kindpour la sécurité des types - Les Cartes d'Agent sont publiées à une URL
.well-known/agent.jsondécouvrable - Les objets d'erreur incluent le booléen
retryableet l'énumération decodetypée - Les transferts de contexte incluent des estimations de tokens et un abandon basé sur la priorité
- Tous les schémas valident un aller-retour : sérialiser → désérialiser → égal à l'original
- Le contenu binaire utilise des références URI, pas d'encapsulation base64
- La rétrocompatibilité est maintenue entre les versions de schéma
- Les événements de streaming incluent des numéros de séquence monotones pour l'ordonnancement
- Aucune donnée sensible dans les métadonnées des messages (utiliser des en-têtes d'authentification appropriés)
LIMITES (NE PAS UTILISER POUR)
Cette compétence ne doit PAS être utilisée pour :
- Sémantique de conversation : Ce que les agents se disent → Utiliser
agent-conversation-protocolsà la place - Topologie d'orchestration : Comment les agents sont connectés → Utiliser
multi-agent-coordinationà la place - Configuration d'infrastructure : Déploiement de l'environnement d'exécution des agents → Utiliser
agentic-infrastructure-2026à la place - Frameworks d'agent unique : Construction d'agents individuels → Utiliser
ai-engineerà la place - Conception d'API : Conception d'API REST/GraphQL → Utiliser
api-design-patternsà la place
Déléguer à :
- Logique de validation de schéma → Utiliser
typescript-advanced-patternspour les types Zod/brandés - Transport réseau → Utiliser
systems-architecturepour la configuration HTTP/WebSocket - Flux d'authentification → Utiliser
auth-patternspour l'implémentation OAuth2/JWT