Tous les articles
IA & dev

OpenAPPA : des garde-fous d'agents IA déterministes, que valent-ils ?

Par Elouan Laurent

OpenAPPA, c'est quoi ? Un filtre déterministe entre l'agent et ses outils

OpenAPPA est un moteur open source (licence MIT) placé entre un agent IA et ses outils. Avant chaque appel, il vérifie une seule chose : les données que l'agent a lues ont-elles le droit d'aller vers cette destination ? Les règles s'écrivent en TOML (un format de configuration lisible), et le même historique donne toujours la même décision.

Le projet vient d'Archestra, qui édite une passerelle pour agents (proxy LLM et passerelle MCP). Son dépôt GitHub date du 18 août 2026. La version 0.31.1 est sortie le 2 octobre. Le projet se décrit comme une « preview » et un « RFC » : sa configuration peut casser d'une version à l'autre.

Le risque visé est l'exfiltration (la sortie de données vers l'extérieur) par injection de prompt, c'est-à-dire des instructions cachées dans un texte que l'agent lit. Un agent qui consulte un dossier RH, puis un forum public piégé, peut envoyer ce dossier par e-mail. OpenAPPA bloque cet envoi sans demander à un modèle de juger l'intention.

Comment OpenAPPA décide : étiquettes, contrats d'outils et plans de secours

Le moteur garde une étiquette de sécurité par session de travail de l'agent. Cette étiquette ne peut que se durcir : une fois qu'une donnée restreinte a été lue, la restriction reste jusqu'à la fin de la session. Deux éléments en forment le cœur :

  • l'audience : qui a le droit de lire les données de la session. Lire un dossier client réduit la liste des destinataires possibles ;
  • la confiance : qui a écrit le texte. Une page web ou le commentaire d'un contributeur extérieur l'abaisse, et les outils qui exigent une entrée fiable sont alors refusés.

OpenAPPA suit aussi les effets déjà produits (un e-mail envoyé) et les approbations demandées pour une action.

Chaque outil a un contrat dans la politique, fait de trois champs :

  • delta : comment le résultat change l'étiquette ;
  • requires : ce que la session doit satisfaire pour autoriser l'appel ;
  • effects : ce qu'on enregistre une fois l'appel réussi.

L'exemple de la documentation tient en deux contrats (extrait adapté) :

[policy]
version = 2

# Lire un fichier RH restreint la session aux lecteurs RH.
[[policy.tool]]
name = "mcp/files/read(path:/hr/*)"
delta = { audience = ["hr@example.com"] }

# Envoyer un e-mail exige que le destinataire soit déjà lecteur autorisé.
[[policy.tool]]
name = "mcp/mail/send"
requires = { audience = { contains = ["$to"] } }
delta = {}

Après la lecture d'un fichier de /hr, l'agent ne peut plus écrire qu'à des destinataires autorisés à le lire. Un outil sans contrat est refusé avant exécution, sauf si la politique déclare un contrat joker (*).

Un blocage n'arrête pas forcément l'agent. OpenAPPA lui renvoie les plans de secours que la politique autorise :

  • nettoyer les champs sensibles avec un sanitizer (un service qui nettoie les données sensibles) ;
  • demander l'approbation d'une personne ou d'un service ;
  • confier la lecture à un sous-agent, qui ne renvoie qu'un résumé nettoyé ;
  • ne pas renvoyer le résultat de l'outil, quand l'intégration le permet.

Un plan peut encore échouer. Si aucun ne passe, l'action reste bloquée.

Les benchmarks : zéro attaque comptée, avec trois réserves

Relevé au 3 octobre 2026 sur la page d'évaluation. Les auteurs annoncent qu'aucune attaque notée n'a réussi sur 1 320 évaluations. Sur Bench-Corp, OpenAPPA termine 88 à 90 % des tâches ; l'article arXiv donne 64,2 à 91 % sur l'ensemble des épisodes.

Ces épisodes viennent de deux suites : Bench-Corp (20 scénarios d'une entreprise simulée : RH, finance, e-mails, forum public) et AgentThreatBench (24 tâches de la suite Inspect Evals). Chaque tâche est jouée avec trois modèles, cinq fois en standard et cinq fois en mode adversarial.

Selon les auteurs, Microsoft FIDES, une autre approche déterministe, laisse passer 28 à 35 % des attaques sur Bench-Corp et termine 37 à 45 % des tâches. Les politiques d'OpenAPPA y appliquent aussi des règles que ces configurations ne gèrent pas.

Le test le plus utile compare OpenAPPA au mode auto de Claude Code, avec le même acteur (Claude Sonnet 5) et un seul essai par tâche :

Configuration Bench-Corp (20 tâches) : terminées / attaques AgentThreatBench (24 tâches) : terminées / attaques
OpenAPPA 75 % / 0 75 % / 0
Auto réglé avec la politique 85 % / 0 95,8 % / 6
Auto d'origine 90 % / 2 87,5 % / 8

« Auto réglé » désigne le mode auto auquel les auteurs ont décrit la politique en langage naturel. Ils reconnaissent que la protection d'OpenAPPA coûte des tâches terminées et des tokens.

Trois réserves avant de conclure :

  1. Ce sont des chiffres de l'éditeur. Bench-Corp est hébergé dans le dépôt d'OpenAPPA, avec ses politiques. Je n'ai exécuté ni le moteur ni les benchmarks.
  2. Le chiffre d'en-tête mélange les acteurs. Le README affiche 89 % de tâches terminées pour OpenAPPA et 90 % pour le mode auto. Le 89 % semble être la moyenne de trois modèles non-Claude (88, 89,5 et 90 %). À acteur identique, OpenAPPA termine 75 % des tâches, contre 85 à 96 % pour Auto.
  3. Les étiquettes sont fournies d'avance. Dans Bench-Corp, les contrats des outils sont écrits à la main pour un monde simulé. Trois scénarios sur vingt passent par un annotateur, et ses réponses sont scriptées (d'après le README du banc). Le test mesure le moteur avec de bonnes étiquettes, pas un annotateur à base de modèle.

Sur Tau Bench, un test de support bancaire sans attaque, OpenAPPA réussit 151 simulations sur 388, contre 156 pour l'agent d'origine. Il consomme 4,22 % de tokens en plus. L'éditeur précise que ce test n'établit pas la sécurité nette.

Déterministe, oui, mais d'où viennent les étiquettes ?

« Déterministe » décrit la décision : mêmes étiquettes, même verdict. Les étiquettes, elles, viennent de contrats statiques ou d'annotateurs.

Un annotateur classe un appel d'outil : qui peut lire ce fichier, ce texte est-il fiable ? Ce peut être un script ou un service que vous écrivez : il reste déterministe tant qu'il n'appelle pas de modèle. Ce peut aussi être un modèle : OpenAPPA intègre trois annotateurs, claude-code, llm et jev.

Ce dernier relie OpenAPPA au modèle de décision de TypeSafe, que j'ai comparé à GLiDE dans mon article sur Jev et GLiDE. Avec builtin = "jev", OpenAPPA envoie chaque appel d'outil à l'API de TypeSafe pour obtenir l'audience et la confiance. La référence des politiques en tire deux conséquences.

D'abord, TypeSafe reçoit le nom de l'outil, sa description et ses arguments. OpenAPPA masque les secrets qu'il reconnaît, mais la documentation parle d'un masquage « best effort », sans preuve d'absence de secret. Pour un garde-fou censé empêcher les fuites, ce point se pèse.

Ensuite, l'annotateur lit des arguments qu'un attaquant peut influencer. OpenAPPA encadre ses réponses par des « permits » : la liste des valeurs qu'un annotateur peut renvoyer, toute réponse hors liste étant refusée. Avec ranks = ["suspicious"], comme dans l'exemple de la doc pour les outils inconnus, il ne peut employer que ce niveau de confiance.

Les permits réduisent l'éventail des erreurs possibles, pas leur probabilité. En clair : le moteur applique fidèlement les étiquettes qu'on lui donne, et une étiquette fausse produit un verdict faux, appliqué de façon déterministe.

La page de comparaison d'OpenAPPA promet « 100% confidence in no data leaks ». Je la lis comme vraie sous réserve que les étiquettes soient justes.

Ce qu'OpenAPPA ne couvre pas

Le contenu des données. OpenAPPA suit leur provenance, pas leur sens. Le README de Bench-Corp précise qu'aucune des deux défenses comparées n'inspecte le contenu par défaut. Dans le scénario d'un secret glissé dans une facture, l'e-mail légitime vers un lecteur autorisé part avec le secret, d'après le commentaire du scénario. Aucune étiquette ne l'arrête.

Les actions dangereuses. OpenAPPA vérifie où les données peuvent aller, pas si une commande est destructrice ou hors de la demande. C'est le rôle du mode auto de Claude Code, dont la documentation indique qu'il réduit les demandes d'approbation sans garantir la sécurité.

Les auteurs d'OpenAPPA proposent de cumuler les deux : OpenAPPA en plancher, le classifieur en second filtre.

La maturité. Le projet compte 36 versions numérotées depuis le 18 août. La documentation n'est pas toujours alignée sur le code. Pour l'export OpenTelemetry (les métriques et journaux pour vos outils de supervision), la page d'intégration dit « en développement » et la page d'observabilité le décrit comme disponible.

L'essayer : Claude Code, agent maison et tests en CI

La voie la plus rapide passe par Claude Code. Selon le README :

curl -fsSL https://openappa.com/install.sh | sh &&
  ~/.local/bin/appa plugin install claude-code

Lisez le script avant de l'exécuter, comme pour tout installeur par curl. La commande clappa démarre ensuite une session protégée, et la commande /appa-guide aide à écrire la politique.

Pour un agent maison, la documentation cite Java parmi les langages possibles. Les références fournies sont pourtant une liaison Python et un exemple Rust. Sur une application Spring Boot, il faudrait écrire le client HTTP (le runtime expose un POST /hook) et l'adaptateur vous-même. L'autre voie est le proxy LLM d'Archestra, dont le support d'OpenAPPA est en bêta.

Le runtime séparé garde son journal d'événements dans SQLite. Je n'ai fait aucun de ces montages.

Le point le plus utile pour une équipe de développement est le test de politique. Deux commandes vérifient que la configuration se charge, puis rejouent des appels d'outils scriptés contre les décisions attendues, sans exécuter les outils :

appa describe --config appa.toml --check
appa replay --config appa.toml policy-tests/

La documentation les montre dans un workflow GitHub Actions, que l'on peut rendre obligatoire pour bloquer une fusion. Une politique de sécurité se relit alors comme du code.

Mon avis : qui peut l'essayer maintenant

OpenAPPA cible une pratique précise : faire juger par un modèle si l'agent peut envoyer des données, et espérer que le verdict résiste aux injections. Son idée centrale, suivre d'où viennent les données plutôt que juger chaque commande, me paraît sensée.

Le choix dépend de votre situation :

  • Un agent de code branché sur des données internes (RH, clients), avec un risque d'exfiltration : essayez le plugin Claude Code avec une politique de test.
  • Un agent maison en Java / Spring Boot : attendez que l'API se stabilise, ou prévoyez le client HTTP à maintenir vous-même (ou le proxy d'Archestra, en bêta).
  • Une crainte de commandes destructrices : ce n'est pas son rôle. Un bac à sable et le mode de permission de votre agent y répondent mieux.

Avant de lui faire confiance, je ferais trois choses :

  1. Lister vos outils et écrire leur contrat. Le travail réel est là : chaque outil doit dire ce qu'il lit et où il peut écrire.
  2. Rejouer vos cas sensibles avec appa replay, en CI, pour que la politique ne dérive pas sans que personne le voie.
  3. Mesurer le taux de tâches terminées de votre propre agent avant et après. L'écart de 75 % contre 85 à 96 % relevé plus haut est un chiffre d'éditeur, pas le vôtre.

Vous voulez brancher des agents IA sur une application Java / Spring Boot sans exposer vos données ? Je développe sur cette stack depuis 2015. Réserver un appel découverte de 30 minutes.

À lire ensuite