Idée en 30 secondes
Eval harness est une méthode pour exécuter le même ensemble de scénarios pour un agent, évaluer les résultats avec les mêmes règles, et comparer candidate à baseline.
Le problème
Sans eval harness, les équipes testent souvent les agents manuellement :
- elles lancent quelques requêtes dans le chat ;
- elles regardent quelques exemples de réponses ;
- elles concluent que le changement semble sûr.
Cela ne donne pas une vision stable : un changement peut paraître correct sur des exemples aléatoires, mais casser des scénarios critiques en production.
Conséquences les plus fréquentes :
- impossible de comparer
candidateetbaselineproprement ; - difficile de reproduire une régression ;
- CI n'a pas de règle claire pour bloquer une release.
Concept principal / modèle
Eval harness n'est pas un test unique, mais une chaîne de validation : dataset figé, conditions de run contrôlées, évaluation, comparaison avec baseline et rapport.
| Composant | Ce qu'il fait |
|---|---|
| Dataset | Stocke un ensemble stable de scénarios et d'attendus |
| Runner | Exécute l'agent sur chaque scénario dans les mêmes conditions et collecte les résultats |
| Evaluators | Applique checks déterministes, LLM-as-a-judge et métriques de qualité |
| Baseline comparator | Compare candidate à baseline |
| Report + CI gate | Produit le résumé et décide pass/fail pour release |
Plus ces composants sont stables, moins il y a de risque que le diff entre candidate et baseline vienne des conditions de run plutôt que d'un vrai changement de comportement.
Comment ça fonctionne
En pratique, eval harness tourne comme une partie de la release pipeline. Chaque changement passe par le même ensemble de scénarios.
Comment se déroule un run eval harness
- Dataset - on charge un ensemble figé de cas.
- Runner - l'agent est exécuté sur chaque cas dans des conditions identiques.
- Evaluators - checks déterministes et, si nécessaire, évaluation LLM-as-a-judge sont appliqués.
- Baseline comparison -
candidateest comparé àbaselinesur les mêmes cas. - Report - un rapport par cas et un résumé global sont sauvegardés.
- Gate - CI autorise ou bloque la release selon les seuils.
Eval harness ne remplace pas les unit tests. Les unit tests valident des composants locaux, le harness valide le comportement du système sur des scénarios complets.
Implémentation
En pratique, eval harness repose sur quelques règles simples. Les exemples ci-dessous sont schématiques et ne dépendent pas d'un framework précis.
1. Structure d'un scénario (test case)
case = {
"id": "price_btc_basic",
"input": "What is the price of BTC?",
"expected_tool": "crypto_price_api",
"checks": ["tool_selection", "valid_output_schema"],
}
Des cas clairs simplifient l'analyse de régression et réduisent l'ambiguïté pendant l'analyse des runs.
2. Runner pour exécuter les cas
def run_case(agent, case):
result = agent.run(case["input"])
return {
"case_id": case["id"],
"selected_tool": result.selected_tool,
"output": result.output,
"stop_reason": result.stop_reason,
}
La nouvelle version et baseline doivent tourner dans des conditions identiques : mêmes timeouts, tool-mocks, limites et configuration d'environnement runtime.
3. Évaluation et comparaison avec baseline
def evaluate_case(run_result, case):
checks = {
"tool_selection": run_result["selected_tool"] == case["expected_tool"],
"valid_output_schema": isinstance(run_result["output"], dict),
}
return {"passed": all(checks.values()), "checks": checks}
candidate = run_eval_suite(agent=candidate_agent, dataset=dataset)
baseline = load_baseline_report("reports/baseline.json")
diff = compare(candidate, baseline)
Pour des tâches ouvertes, on ajoute en général LLM-as-a-judge aux checks déterministes, comme couche séparée d'évaluation.
Baseline doit aussi être versionné et lié à un modèle, un prompt et une configuration runtime précis.
4. Rapport et CI gate
summary = build_summary(candidate, diff)
if summary["task_success_rate"] < 0.92:
fail("gate_failed:task_success_rate")
if summary["hallucination_rate"] > 0.03:
fail("gate_failed:hallucination_rate")
write_json("reports/eval-summary.json", summary)
Un bon eval harness sauvegarde toujours des artefacts : résultats par cas, raisons des échecs, diff contre baseline et rapport final.
5. Release gate dans la stratégie globale
Les critères de blocage de release et les seuils du CI gate sont définis séparément dans Testing Strategy, pour éviter les duplications dans chaque article.
Erreurs typiques
Dataset instable
Les scénarios changent en continu "en cours de route", donc les résultats entre runs ne sont plus comparables.
Cause typique : dataset non versionné et sans IDs de cas fixes.
Version de modèle non figée
Les providers LLM mettent parfois à jour les modèles sans changer leur nom générique.
Si la version n'est pas figée (par exemple gpt-4o-2024-08-06), les résultats peuvent varier entre runs.
Cause typique : alias de modèle (gpt-4o, sonnet) utilisé sans version pinning.
Dans les systèmes de production, on fixe en général une version de modèle précise ou une version snapshot.
Exécution manuelle au lieu d'automatisation
Harness est lancé seulement quand "on a le temps", pas à chaque changement important.
Cause typique : pas d'intégration CI et pas de pass/fail gate clair.
Pas de comparaison avec baseline
L'équipe regarde uniquement les métriques absolues de candidate et laisse passer des régressions discrètes.
Cause typique : le rapport ne contient pas de diff entre candidate et baseline.
Checks déterministes et non déterministes mélangés
Checks déterministes et LLM-as-a-judge sont mélangés dans un "score global", donc il est difficile de savoir ce qui a cassé.
Cause typique : pas de sections d'évaluation séparées selon le type de check.
Pas d'artefacts de run
On n'a qu'un pourcentage final de succès, sans traces ni checks par cas.
Cause typique : harness ne sauvegarde pas de résultats détaillés dans les fichiers de rapport.
Runs eval instables
Le même cas passe parfois et échoue parfois, donc l'équipe ne fait plus confiance au rapport.
Cause typique : environnement externe instable, mocks manquants, timeouts fluctuants ou conditions de run non uniformes.
En bref
- Eval harness rend le test d'agents reproductible et comparable.
- La décision de release doit s'appuyer sur le diff
candidatevsbaseline, pas sur des exemples manuels. - Les artefacts par cas comptent autant que les métriques globales.
- Sans CI gate, eval harness devient un "rapport pour le rapport".
FAQ
Q : Eval harness, c'est juste un ensemble de tests ?
R : Non. C'est un processus piloté : dataset, runner, evaluators, comparaison avec baseline et CI gate.
Q : Peut-on se passer de LLM-as-a-judge ?
R : Oui, si les tâches sont bien couvertes par des checks déterministes. Pour les tâches ouvertes, LLM-as-a-judge est en général ajouté comme couche d'évaluation séparée.
Q : À quelle fréquence lancer eval harness ?
R : Au minimum à chaque changement pouvant affecter le comportement de l'agent : modèle, prompts, tools, ou règles runtime.
Q : Qu'est-ce qui est le plus important dans la première version du harness ?
R : Un dataset stable, un baseline sauvegardé, des seuils pass/fail clairs et les artefacts de run.
Et ensuite
Pour la vue d'ensemble, commencez par Testing Strategy. Ensuite couvrez la logique critique via Unit Testing, construisez un Golden Datasets stable, et ajoutez Regression Testing pour les changements entre versions.
Quand les premiers incidents réels apparaissent, ajoutez Replay and Debugging et intégrez ces cas au dataset de votre eval harness.