8 min de lecture

Tester les échecs des outils d'agents : détecter tôt les nouvelles tentatives dangereuses

Les tests des échecs d'outils d'agents exigent plus que des assertions d'erreur. Utilisez une matrice pratique pour les identifiants expirés, les refus, les données incorrectes, les délais d'attente et les interruptions SSH.

Tester les échecs des outils d'agents : détecter tôt les nouvelles tentatives dangereuses

Les tests des échecs d'outils d'agents doivent surtout vérifier ce que l'agent croit après l'échec d'une opération, et pas seulement si l'outil a émis une erreur. Un outil qui signale « la requête a échoué » après une écriture distante qui a peut-être abouti crée un problème plus grave qu'un outil qui s'arrête avec une réponse incomplète. Les agents planifient leurs actions à partir du résultat que vous leur fournissez.

Le scénario nominal masque les décisions qui déterminent si une exécution autonome est sûre : réessayer, demander une approbation, renouveler un accès, réparer les données ou s'arrêter. J'ai vu des suites d'outils avec des centaines de tests au vert qui n'avaient jamais provoqué de coupure réseau entre le démarrage d'une commande distante et le retour de sa sortie. Ces suites ne testaient pas la partie dangereuse.

La réponse à un échec devient une entrée pour le planificateur de l'agent

Un agent considère le résultat d'un outil comme un élément de preuve. Si le résultat laisse penser qu'aucune modification n'a eu lieu, l'agent peut réessayer. S'il indique qu'un identifiant a expiré, l'agent peut chercher une procédure de récupération autorisée. S'il indique une réussite alors que le résultat distant est inconnu, l'agent peut fonder plusieurs actions ultérieures sur une fiction.

Séparez les échecs selon ce que l'appelant peut savoir. Cette distinction est constamment brouillée :

  • Un refus confirmé signifie que le service distant a reçu la requête et l'a rejetée.
  • Un échec confirmé signifie que le service distant a renvoyé un résultat indiquant qu'il n'a pas effectué le travail demandé.
  • Un résultat incertain signifie que l'appelant ne peut pas établir si le système distant a effectué le travail.
  • Un échec local signifie que l'outil a échoué avant de pouvoir effectuer une tentative distante significative.

Un refus de connexion avant l'ouverture d'une session TCP correspond généralement à un échec local. Une réponse HTTP 403 est un refus confirmé. Un délai de lecture dépassé après l'envoi d'un POST produit un résultat incertain, sauf si le service distant permet de rechercher l'opération. Ces catégories doivent apparaître dans vos cas de test et dans le schéma de résultat de l'outil. Ne les dissimulez pas dans une phrase que l'agent devrait interpréter.

Une structure de résultat compacte rend le contrat testable :

{
  "ok": false,
  "category": "outcome_unknown",
  "operation": "create_deployment",
  "retry": "reconcile_first",
  "correlation_id": "case-ssh-017",
  "message": "Connection closed after the remote command started; remote completion is unknown."
}

Les noms importent peu. La séparation, elle, est essentielle. retry: "never" pour un refus d'autorisation et retry: "reconcile_first" pour une écriture dont le délai a expiré indiquent des choses différentes à l'agent, sans transformer tout le message d'erreur en prompt.

Ne renvoyez pas les erreurs brutes du fournisseur comme seule interface. Elles changent, contiennent souvent du texte sans intérêt et peuvent parfois inclure des éléments de la requête que vous ne devriez pas transmettre à un agent. Conservez le statut, le corps et les en-têtes d'origine dans des diagnostics protégés. Renvoyez à l'appelant un résultat stable et volontairement limité.

Construisez la matrice autour des opérations et des preuves

Une matrice utile croise chaque opération avec les modes d'échec susceptibles d'en changer le sens. Commencez par répertorier les outils qui lisent, créent, mettent à jour, suppriment, déclenchent ou exécutent. Une lecture dont le délai expire n'a pas la même règle de récupération qu'une commande qui modifie un hôte de production.

Utilisez cette matrice comme point de départ. Remplacez les noms d'opérations et les résultats attendus par les vôtres, mais ne supprimez pas la colonne « effet distant connu ». Elle force les cas inconfortables à apparaître clairement.

CasOpérationCondition injectéeEffet distant connu ?Catégorie attendueInstruction pour l'agent
C01lire un ticketÉchec de la résolution DNSoui, aucune requête envoyéelocal_failureréessayer dans une limite définie
C02créer un ticketJeton expiréoui, requête rejetéeauthentication_faileds'arrêter et demander une récupération d'identifiant autorisée
C03supprimer une versionPermission refuséeoui, requête rejetéeauthorization_deniedne pas réessayer
C04lire une compilationLe JSON contient status: 7oui, réponse reçuemalformed_responses'arrêter et signaler une incompatibilité de schéma
C05créer un déploiementRéponse retardée au-delà de la limite du clientnonoutcome_unknownréconcilier avant de réessayer
C06exécuter un redémarrage SSHL'assistant local s'est arrêté après le démarrage distantnonoutcome_unknownvérifier l'état distant avant une autre commande
C07mettre à jour un enregistrementLe service renvoie 429oui, requête rejetéerate_limitedattendre selon les instructions, puis réessayer si c'est sûr

Ajoutez des lignes pour les opérations qui dépensent de l'argent, modifient des permissions, renouvellent des identifiants ou touchent à un état partagé. Ces opérations nécessitent plusieurs lignes liées aux délais d'attente. Testez un délai dépassé avant que les octets ne quittent le processus, après l'envoi des en-têtes, après l'acceptation de la requête par le service et pendant l'arrivée du corps de la réponse. Les points d'injection précis dépendent du protocole, mais les réduire à un cas générique de « délai dépassé » fait perdre le comportement à vérifier.

Chaque ligne nécessite quatre assertions :

  1. Vérifiez la catégorie du résultat de l'outil et l'instruction de nouvelle tentative.
  2. Vérifiez l'action suivante de l'agent, notamment l'absence de nouvelle tentative destructive improvisée.
  3. Vérifiez l'état distant ou la raison documentée pour laquelle il reste inconnu.
  4. Vérifiez que la piste d'événements contient l'identifiant de corrélation et le résultat observé.

Cela demande plus de travail que de vérifier ok == false. Cela permet aussi de détecter les problèmes qui comptent après que l'agent a déjà effectué plusieurs actions.

Les identifiants expirés et les actions refusées exigent des récupérations différentes

Un identifiant expiré ou révoqué prouve que l'authentification a échoué. Une action refusée prouve que l'appelant a été authentifié, mais qu'il n'a pas l'autorisation d'effectuer cette opération, sauf si le fournisseur masque volontairement la distinction. Traiter les deux cas comme un simple « échec d'accès » entraîne un mauvais comportement de l'agent.

La norme RFC 9110 définit 401 comme une requête non authentifiée et exige que le serveur envoie un défi WWW-Authenticate. Elle définit 403 comme un refus d'exécuter la requête, même lorsque le serveur n'en révèle pas la raison. Les fournisseurs ne respectent pas toujours clairement cette distinction, alors testez la réponse réelle du fournisseur. Votre outil doit néanmoins faire correspondre les éléments observés à des catégories distinctes lorsqu'il peut le faire honnêtement.

Pour tester un identifiant expiré, utilisez un identifiant accepté pendant la préparation, puis rejeté lors de l'appel réel. Une chaîne factice que le service n'a jamais reconnue ne teste que la branche d'un identifiant invalide. Vous voulez détecter les différences de comportement des caches, du code de renouvellement et des convertisseurs d'erreurs lorsqu'un jeton d'accès a réellement expiré.

Un simple scénario de test peut représenter les deux cas sans exposer de secret :

cases:
  - id: expired-token
    request:
      method: POST
      path: /v1/releases
    fixture_response:
      status: 401
      headers:
        www-authenticate: Bearer error="invalid_token"
      body: {"error":"token_expired"}
    expect:
      category: authentication_failed
      retry: never
      secret_in_result: false

  - id: denied-release
    request:
      method: POST
      path: /v1/releases
    fixture_response:
      status: 403
      body: {"error":"insufficient_scope"}
    expect:
      category: authorization_denied
      retry: never
      secret_in_result: false

L'assertion secret_in_result détecte une erreur qui apparaît pendant un débogage précipité : le code ajoute à une exception l'en-tête d'autorisation envoyé ou l'objet de configuration. Testez la sortie sérialisée de l'outil, les traces et la transcription qui parvient à l'agent. La suppression d'un secret dans un journal ne protège pas les autres.

Ne demandez pas à l'agent « d'essayer un autre identifiant » sauf si votre système lui fournit explicitement une identité distincte et autorisée. La sélection aveugle d'identifiants peut franchir une limite de privilège tout en donnant l'impression de résoudre un problème de disponibilité. Un test doit prouver qu'un échec d'authentification arrête l'exécution ou l'oriente vers la procédure de récupération humaine approuvée.

Les données malformées exigent un test de contrat, pas seulement un test de parseur JSON

Les données malformées comprennent les JSON valides que votre code ne peut pas utiliser sans risque. La syntaxe invalide est le cas le plus simple. En production, les problèmes viennent plus souvent d'un champ dont le type change, de la disparition d'un identifiant obligatoire, du remplacement d'une enveloppe de réussite par une enveloppe d'erreur ou d'une réponse tronquée après la fermeture d'une connexion par un proxy.

La spécification JSON-RPC 2.0 sépare les erreurs d'analyse (-32700) des requêtes invalides (-32600). Cette distinction est utile, car elle sépare des octets illisibles d'un message lisible qui viole le protocole. Appliquez la même rigueur à vos réponses métier : la réussite du parseur ne prouve pas que la réponse respecte le contrat de l'outil.

Pour chaque réponse de fournisseur que vous consommez, écrivez des scénarios qui violent une seule hypothèse à la fois :

  • Remplacez un identifiant texte par null, un nombre puis un objet.
  • Omettez un champ dont les appels suivants ont besoin pour la réconciliation.
  • Renvoyez un statut de réussite avec un corps ayant la forme d'une erreur.
  • Renvoyez un statut d'erreur avec un corps HTML ou un document JSON tronqué.
  • Dupliquez un élément ou modifiez l'ordre lorsque votre code sélectionne le premier élément.

Vérifiez ensuite le comportement exact. L'outil doit nommer le champ ou la condition de contrat en échec dans les diagnostics protégés, renvoyer malformed_response à l'agent et n'effectuer aucune modification ultérieure à partir de valeurs devinées.

Un mauvais schéma courant semble inoffensif : response.id || request.id. Il permet au workflow de continuer lorsqu'un fournisseur omet id, mais peut provoquer une mise à jour ou une suppression sur un objet sans rapport si l'identité de la requête et celle de la réponse diffèrent. Testez que l'absence de l'identité dans la réponse arrête l'opération. Un workflow interrompu coûte moins cher qu'une écriture incorrecte.

Les clients d'outils MCP exigent la même attention. Le format de résultat des outils du Model Context Protocol prend en charge le signal isError pour un échec au niveau de l'outil. Utilisez-le lorsque l'outil lui-même ne peut pas effectuer le travail promis, tout en conservant un contenu suffisamment précis pour que l'agent choisisse une branche sûre. Ne masquez pas une réponse amont malformée derrière un résultat textuel normal commençant par « Error: ». De nombreux clients considéreront alors l'exécution de l'outil comme réussie et laisseront l'agent deviner la suite.

Les délais d'attente deviennent ambigus dès qu'une écriture commence

Contrôlez chaque appel risqué
Marquez les clés d'API sensibles pour demander une approbation à chaque utilisation, y compris lors d'une nouvelle tentative après un résultat incertain.

Un délai d'attente vous indique que votre limite a expiré. Il ne révèle pas l'état de l'opération distante. Cela semble évident jusqu'à ce qu'une boucle de nouvelles tentatives transforme discrètement une réponse perdue en facture dupliquée, en deux déploiements ou en un second redémarrage.

Testez le comportement à la frontière où la certitude change. Votre injecteur d'erreurs ou votre faux service doit enregistrer chaque étape :

case=C05 request_id=case-http-005 received=true
case=C05 request_id=case-http-005 mutation_committed=true
case=C05 response_write=delayed
client case=C05 deadline_exceeded=true

L'assertion attendue n'est pas « le client a reçu un délai d'attente ». Elle vérifie que le client renvoie outcome_unknown, n'émet pas un second POST et utilise une recherche d'état ou un mécanisme d'idempotence avant de poursuivre.

Les jetons d'idempotence ne sont utiles que si l'API distante les documente et les respecte pour l'opération concernée. Testez-les comme une séquence complète : envoyez une requête avec un jeton unique, retardez la première réponse jusqu'à ce que l'appelant abandonne, envoyez le même jeton via la procédure de récupération, puis vérifiez que le service signale une seule opération logique. Ne prétendez pas qu'une opération est idempotente parce que vous avez ajouté un en-tête ignoré par le fournisseur.

Pour les opérations sans point de réconciliation ni prise en charge de l'idempotence, indiquez-le dans le résultat de l'outil. L'action sûre peut consister à s'arrêter et à demander à une personne d'inspecter le système distant. Ce n'est pas un échec d'ingénierie. Prétendre être certain parce qu'un workflow veut continuer en est un.

Définissez des délais par phase lorsque votre client le permet : connexion, écriture de la requête, premier octet de réponse et durée totale de l'opération. Une seule limite importante masque le fait qu'un pair n'a jamais accepté la connexion ou qu'il a accepté l'écriture avant de se bloquer. Vos tests n'ont pas besoin d'exposer chaque phase à l'agent, mais vos diagnostics doivent contenir suffisamment de détails pour qu'un opérateur puisse reproduire l'événement.

Les commandes distantes interrompues doivent conserver l'incertitude

Une commande SSH présente une fenêtre d'échec que les développeurs HTTP sous-estiment souvent. Le client peut envoyer la commande, le shell distant peut la démarrer, puis la connexion peut se fermer avant que l'appelant ne reçoive le code de sortie. Le crash d'un processus local ou la perte d'une route réseau n'annule pas le travail déjà commencé sur l'hôte distant.

OpenSSH précise que son client renvoie le code de sortie de la commande distante lorsqu'il peut l'obtenir. Lorsque le transport se rompt avant cela, l'appelant ne dispose pas de ce code. Testez volontairement ce cas au lieu de considérer qu'un code de sortie local non nul prouve l'échec de la commande distante.

Créez une commande de test distante qui écrit un marqueur de début, attend, écrit un marqueur de fin et produit un résultat reconnaissable. Arrêtez ensuite le transport local pendant l'attente. Limitez ce test à un hôte ou à un conteneur isolé qui vous appartient.

# remote command used only in an isolated test environment
id="case-ssh-017"
printf '%s start\n' "$id" >> /tmp/agent-tool-test.log
sleep 20
printf '%s complete\n' "$id" >> /tmp/agent-tool-test.log

Exécutez la commande par le même chemin SSH que celui utilisé par l'outil, attendez l'apparition du marqueur de début, puis arrêtez l'assistant local. Une fois l'attente distante terminée, inspectez le journal. Exécutez le test deux fois : une fois lorsque le processus distant termine son travail et une fois lorsque le système distant l'arrête après le marqueur de début. Les deux cas produisent une interruption locale, mais exigent des récupérations différentes.

Pour les commandes qui modifient l'état, concevez une commande de réconciliation avant de concevoir une nouvelle tentative. Un redémarrage de service peut interroger la durée de fonctionnement du processus ou la révision du déploiement. Une installation de paquet peut interroger la version installée. Une commande qui ne peut pas être réconciliée doit nécessiter une intervention humaine explicite après une interruption.

Évitez les extraits shell qui masquent une exécution partielle derrière des chaînes && et une sortie vague. Émettez un identifiant d'opération durable avant le début de la partie modificatrice et réutilisez cet identifiant lors de l'inspection. Si l'environnement distant ne peut conserver aucun marqueur, l'outil n'a aucun fondement pour dire à un agent qu'une nouvelle tentative est sûre.

Les refus humains sont un résultat normal, pas un test défectueux

Gardez les clés SSH en local
Faites passer SSH par sp-ssh pendant que Sallyport conserve la clé et ne renvoie que le résultat de la commande.

Le refus d'une action par une personne doit produire un résultat distinct qui clôt proprement cette branche. Les équipes vérifient souvent qu'un écran d'approbation s'affiche, mais oublient de tester le refus. Les agents se mettent alors à réessayer, à reformuler la même demande ou à présenter un échec d'approbation comme un problème réseau.

Testez le refus à chaque frontière d'autorisation que vous exposez. Vérifiez que l'outil ne se connecte pas au service distant après un refus. Vérifiez qu'il ne conserve pas une approbation pour un processus ultérieur ou pour une autre action nécessitant une nouvelle décision. Vérifiez que l'agent reçoit un texte qu'il peut utiliser sans considérer le refus comme une invitation à chercher un contournement.

Le coffre de Sallyport refuse toute action lorsqu'il est verrouillé. Ses approbations de session et par appel permettent de tester ces décisions sans placer les identifiants dans le processus de l'agent. Cette séparation est utile, car un coffre verrouillé, une session refusée et une utilisation par appel refusée peuvent tous interrompre une opération pour des raisons différentes.

La lassitude face aux approbations constitue un échec de test à part entière. Si une lecture inoffensive génère des demandes répétées pendant une exécution normale, les utilisateurs finiront par approuver sans lire. Si un appel destructeur hérite accidentellement d'une approbation trop large, les utilisateurs ne voient jamais le point de décision attendu. Testez le nombre, le moment et la portée des demandes, pas seulement leur présence.

Utilisez un agent de test qui tente une action approuvée, une action refusée et une action après la fin du processus. Le dernier appel détecte les états d'approbation qui persistent au-delà de la session prévue. Ne simulez pas cela uniquement en modifiant un booléen en mémoire ; lancez un processus distinct afin que le test reproduise le cycle de vie réel de vos utilisateurs.

Les journaux doivent expliquer ce qui s'est passé sans exposer les accès

Arrêtez le travail au niveau du coffre
Son coffre reste verrouillé derrière Secure Enclave et Touch ID, et refuse toute action tant qu'il n'est pas ouvert.

Un enregistrement d'échec utile permet de reconstituer la causalité : quelle exécution d'agent a tenté quelle opération, quel identifiant de requête elle a utilisé, ce que le système distant a observé, ce que l'outil a renvoyé et ce que l'agent a fait ensuite. Il ne devrait pas contenir l'identifiant qui a autorisé l'appel.

Enregistrez un événement à chaque point où la réponse peut changer. Pour une écriture dont le délai expire, consignez la construction de la requête, le début de l'envoi, l'acceptation distante si votre scénario peut la signaler, l'expiration du délai, la tentative de réconciliation et la classification finale. Incluez un identifiant de corrélation généré avant la première action réseau. Ne le dérivez pas d'un secret et ne le réutilisez pas pour plusieurs opérations.

Ce format convient à un banc de test local :

{"time":"2025-04-12T10:18:03Z","case":"C05","id":"case-http-005","event":"dispatch_started"}
{"time":"2025-04-12T10:18:03Z","case":"C05","id":"case-http-005","event":"remote_committed"}
{"time":"2025-04-12T10:18:08Z","case":"C05","id":"case-http-005","event":"client_timeout"}
{"time":"2025-04-12T10:18:08Z","case":"C05","id":"case-http-005","event":"result","category":"outcome_unknown"}

Votre assertion peut alors comparer les enregistrements du client et du scénario à l'aide de id. Si le scénario indique remote_committed alors que l'outil indique confirmed_failure, faites échouer le test. Ce désaccord révèle une affirmation dangereuse, même si tous les chemins de code ont renvoyé un objet d'erreur bien formé.

Pour une piste dont l'intégrité peut être vérifiée, testez aussi la vérification. Sallyport produit ses enregistrements de session et d'activité à partir d'un journal d'audit chiffré organisé en chaîne de hachage, et sp audit verify vérifie cette chaîne hors ligne sans nécessiter de clé de coffre. Un test d'échec doit ajouter une séquence d'événements connue, la vérifier, modifier une copie d'un enregistrement et confirmer que la vérification échoue sur la copie modifiée.

Ne placez pas par défaut les corps complets des requêtes dans les journaux ordinaires. Les données de requête contiennent souvent des informations personnelles, du code source ou des jetons ajoutés par inadvertance. Journalisez le nom de l'opération, la classification de la cible, l'identifiant de corrélation, la catégorie du résultat et une référence vers les diagnostics protégés. N'étendez la collecte que dans un environnement de test contrôlé où vous connaissez le contenu des scénarios.

Testez le comportement de récupération de l'agent, pas seulement l'adaptateur

Les tests unitaires prouvent qu'un adaptateur convertit 403 en authorization_denied. Ils ne prouvent pas que l'agent s'arrête après réception de ce résultat. Exécutez une petite suite de bout en bout avec une instruction d'agent déterministe et un faux service distant qui expose le journal des événements injectés.

Donnez à chaque exécution une tâche limitée et une frontière explicite. Par exemple : créer un enregistrement, le relire, puis lui ajouter une note. Retardez la réponse de création après avoir enregistré l'enregistrement. Le comportement correct de l'agent consiste à effectuer une recherche par identifiant de corrélation ou par jeton d'idempotence avant de tenter une seconde création. Le test doit échouer s'il crée un autre enregistrement, même s'il finit par accomplir la tâche.

Conservez le prompt de l'agent inchangé pour cette suite. Si vous modifiez en même temps le prompt, le contrat de l'outil, le comportement du scénario et la version du modèle, un échec vous apprendra peu de choses. Enregistrez la transcription de l'outil et l'appel suivant de l'agent, puis comparez-les aux transitions autorisées :

create -> outcome_unknown -> lookup_by_request_id -> found -> attach_note
create -> outcome_unknown -> create

La première transition n'est autorisée que si la recherche confirme la création initiale. La seconde est un échec. Cette vérification par machine à états est plus utile que d'évaluer si la réponse finale semblait raisonnable.

Exécutez les cas déterministes de la matrice à chaque modification du code des outils, des schémas de résultats, de la gestion des autorisations ou de la logique de nouvelles tentatives. Répétez les cas d'interruption dans une infrastructure isolée, car l'ordonnancement influe sur leur résultat. Lorsqu'un nouvel incident apparaît, ajoutez sa reproduction minimale à la matrice avant de le corriger. Sinon, le même chemin de récupération séduisant mais incorrect réapparaîtra lors de la prochaine refactorisation.

Le critère d'un outil n'est pas de continuer après chaque incident. Il doit dire la vérité sur ce qu'il sait, laisser des preuves et refuser de transformer une incertitude en seconde action destructive.

FAQ

Que doit contenir une matrice de tests des échecs pour les outils d'agents IA ?

Une matrice utile croise le type d'opération avec le type d'échec et le comportement attendu du client. Incluez la requête, l'erreur injectée, les éléments observés au niveau du transport, le résultat attendu de l'outil, la règle de nouvelle tentative et l'enregistrement d'audit attendu. Si une ligne ne permet pas de dire si le système distant a pu être modifié, elle n'est pas prête à être automatisée.

Comment tester des identifiants d'API expirés pour un agent ?

Traitez l'expiration d'un identifiant comme un échec d'authentification dont la résolution exige un nouvel identifiant, et non comme une nouvelle tentative aveugle. Testez la réponse réelle fournie par votre prestataire, y compris les en-têtes et la structure du corps, car un service peut utiliser 401 tandis qu'un autre renvoie une erreur qui lui est propre. Vérifiez que l'agent ne reçoit jamais le nouveau secret pendant le traitement du résultat.

Quelle différence y a-t-il entre un identifiant expiré et une action refusée ?

Une action refusée signifie que l'identité peut être valide, mais que l'opération demandée n'est pas autorisée. Testez-la séparément d'un identifiant expiré, car le comportement attendu diffère : arrêtez l'opération, signalez le refus et ne demandez pas de renouvellement du secret. Une nouvelle tentative peut transformer un refus clair en trafic inutile ou en sollicitations d'approbation répétées.

Comment tester les réponses d'API malformées produites par un outil ?

Renvoyez un JSON syntaxiquement valide contenant des types incorrects, des champs obligatoires manquants ou une structure d'erreur modifiée. Les analyseurs qui testent uniquement le JSON invalide passent à côté des problèmes qui apparaissent souvent en production. L'outil doit rejeter les données inutilisables avec une erreur précise et ne doit pas inventer les identifiants ou les statuts manquants.

Est-il sûr de relancer un appel d'outil après un délai d'attente ?

Non. Un délai d'attente signifie seulement que l'appelant a cessé d'attendre. Le service distant peut avoir terminé la requête, être encore en train de l'exécuter ou ne jamais l'avoir reçue. Testez ces trois possibilités et exigez une réconciliation avant de relancer une opération qui modifie des données.

Comment simuler l'interruption d'une commande SSH ?

Arrêtez l'outil SSH local après le début de la commande distante et conservez la sortie de cette commande dans un emplacement que votre test peut inspecter. Vous créez ainsi l'ambiguïté que les tests ordinaires de refus de connexion ne permettent pas de reproduire. L'agent doit signaler un résultat inconnu plutôt que prétendre que la commande a réussi ou échoué.

Comment tester le refus d'une action d'agent par un utilisateur ?

Testez le refus d'approbation comme une branche distincte, avec une personne qui décline la demande au niveau prévu. L'agent doit recevoir un résultat de refus clair, arrêter sa branche actuelle et éviter de répéter les demandes pour la même action. Un test qui vérifie seulement l'apparition de la boîte de dialogue ne prouve rien de tout cela.

Quels journaux faut-il pour diagnostiquer les échecs d'un outil ?

Utilisez des identifiants de corrélation uniques et recueillez les événements du client, de l'injecteur d'erreurs et du service distant. Comparez la requête tentée, l'effet observé à distance, le résultat renvoyé et l'appel suivant de l'agent. Des journaux qui enregistrent uniquement l'erreur finale ne permettent pas de comprendre une écriture interrompue.

Les outils d'agents doivent-ils renvoyer une erreur générique pour tous les échecs ?

Non. Un bloc catch générique masque la différence entre un refus, une mauvaise réponse, une défaillance de connexion et une écriture incertaine. Fournissez à l'agent un petit vocabulaire d'erreurs stable, puis conservez les détails techniques dans les journaux destinés à l'opérateur. Cette séparation aide l'agent à planifier sans effacer les preuves.

À quelle fréquence faut-il exécuter les tests d'échec des outils d'agents ?

Exécutez les cas d'échec déterministes à chaque modification, puis répétez les cas liés au temps et aux interruptions dans un environnement isolé. Les problèmes de concurrence et les écritures partielles nécessitent plusieurs essais, car l'ordonnancement compte. N'attendez pas un incident en production pour découvrir que l'outil affirme une certitude qu'il n'a pas.

Sallyport

Sallyport exécute les appels d'API et les commandes SSH à la place de votre agent IA. Les clés restent dans un coffre-fort local sur votre Mac ; vous approuvez chaque exécution et chaque action est consignée dans un journal scellé.

© 2026 Sallyport · Open source sous Apache-2.0 · Oleg Sotnikov