Skip to content

ADR-0003: Arnés de evaluación

  • Estado: Accepted
  • Fecha: 2026-03-18
  • Responsables de la decisión: Waldemar Szemat

El arnés de evaluación es el centro de este proyecto. El agente es el vehículo; el arnés es el artefacto. Un lector tiene que quedar convencido de que el arnés es real: carga datasets de referencia JSONL, ejecuta el agente de extremo a extremo, emite trazas por turno, puntúa esas trazas a lo largo de un conjunto de dimensiones de evaluación deterministas y respaldadas por el juez, y produce un veredicto que bloquea el PR más un informe de formato más extenso.

Ninguna de las “plataformas de evaluación de agentes” listas para usar cubre todas estas dimensiones para un agente multi-turno del dominio de salud. DeepEval aporta una métrica de alucinación sólida; un LLM-como-juez de Anthropic Claude Haiku puntúa las dimensiones basadas en rúbrica (fundamentación, fidelidad, tono y empatía); Phoenix da un backend OTel con interfaz de trazado; Promptfoo es el runner canónico de red-team / OWASP LLM Top 10. Un núcleo pytest hecho a mano que orquesta estas piezas es la menor cantidad de pegamento que entrega cada dimensión mientras se mantiene portable.

¿Cómo estructuramos el arnés de evaluación para que (a) corra como un job normal de pytest en CI, (b) los evaluadores deterministas bloqueen cada PR de forma barata, (c) el LLM-como-juez corra cada noche sin reventar el presupuesto del nivel gratuito, (d) los escenarios de red-team corran cada noche fuera de banda y (e) cada evaluador pueda cambiarse o actualizarse sin reescribir el runner?

  • Cobertura de las dimensiones de evaluación a las que el proyecto se compromete
  • Techo de costo de la compuerta del PR: solo evaluadores deterministas en cada PR; LLM-como-juez cada noche
  • Reproducibilidad: un contribuidor debe poder correr la suite de evaluación localmente y obtener el mismo veredicto que da CI
  • Fijar el modelo juez con exactitud (proveedor + modelo + versión) para que la puntuación sea estable entre corridas
  • Higiene de licencias: cada biblioteca de evaluación debe tener licencia permisiva (Apache 2 / MIT / ELv2 aceptables para herramientas)
  • Evitar una “plataforma de evaluación de IA” SaaS de caja negra; el arnés tiene que ser portable y autoalojado
  • Núcleo pytest hecho a mano + DeepEval + un LLM-como-juez de Anthropic + Promptfoo + Phoenix con un modelo Anthropic Claude Haiku fijado como el juez (elegida)
  • Un SaaS de un proveedor (Braintrust / Galileo / LangSmith Eval)
  • DeepEval puro como el arnés completo, con sus runners integrados de dataset e informe
  • OpenAI Evals como el runner

Opción elegida: núcleo pytest hecho a mano que orquesta DeepEval, un LLM-como-juez de Anthropic, Promptfoo y Phoenix, con un modelo Anthropic Claude Haiku fijado como el juez LLM (id del modelo detrás de una bandera de entorno, versión fijada). El arnés tiene tres flujos de trabajo:

  • Bloqueo del PR: solo evaluadores deterministas (cobertura de citaciones, corrección de citaciones, coincidencia de plantilla de rechazo, coincidencia de lista de escalamiento, recall de recuperación). No requieren LLM ni clave de API, así que la compuerta es barata y totalmente reproducible. Los umbrales de corpus respaldados por el juez se evalúan en el flujo de trabajo nocturno del juez, no en la compuerta del PR.
  • LLM-como-juez nocturno (programado): el juez fijado Anthropic Claude Haiku puntúa las dimensiones basadas en rúbrica (fundamentación, fidelidad y las rúbricas de tono / empatía / idoneidad médica), y DeepEval aporta su métrica de alucinación. Este es el único flujo de trabajo que gasta tokens del juez.
  • Red-team (flujo de trabajo separado): dos capas. (a) Una compuerta de CI determinista y sin claves — una evaluación de Promptfoo de los 13 casos adversariales hechos a mano; el shim conduce el agente real de LangGraph usando un cliente stub fuera de línea; la capa de barreras de seguridad del agente decide, no el LLM. (b) Una medición en vivo con clave separada — una corrida de red-team de Promptfoo con Groq llama-3.3-70b-versatile como objetivo, OpenAI gpt-4o como generador de ataques y Groq como evaluador. No bloqueante; se esperan fallas reales y se documentan con procedencia.

Phoenix es el sumidero de observabilidad durante las corridas de evaluación: cada turno emite spans OTel a través del cableado OpenInference existente del proyecto (ver ADR-0006), Phoenix los recolecta, y el arnés adjunta las URLs de traza de Phoenix al informe de evaluación. Inspect AI (UK AISI) queda reservado como una tarea bonus de evaluación de capacidades, opcional para el hito inicial.

Esta composición le da a cada dimensión de evaluación un hogar concreto, mantiene barata la compuerta del PR y nunca depende de una plataforma de evaluación cerrada.

  • La suite de evaluación corre el subconjunto de bloqueo del PR localmente y en CI; el job de CI falla en las violaciones de umbral configuradas
  • Cada evaluador se implementa detrás de un pequeño Protocol Scorer; el runner no importa las bibliotecas de evaluadores directamente
  • El proveedor del juez es Anthropic y el id del modelo juez se lee de una variable de entorno JUDGE_MODEL; el juez en vivo se construye con esa variable vacía, de modo que un id mal escrito recae en el valor por defecto fijado Claude Haiku del adaptador (falla cerrada) en lugar de fallar en modo abierto ante una cadena de modelo inválida
  • Un informe nocturno de red-team se publica como artefacto

El juez evalúa cinco dimensiones de rúbrica específicas de features cuando un caso golden lleva etiquetas de feature en sus metadatos. Las features son: voice, i18n (internacionalización), pii (redacción de PII), governance (cobertura regulatoria) y data_layer (control de claves de la capa de datos / visualización de costos).

  • Un conjunto de plantillas de rúbrica de feature define las cinco descripciones de rúbrica de feature, cada una con sus propios criterios de puntuación graduados.
  • El evaluador de fundamentación extiende condicionalmente su rúbrica con entradas de feature cuando un caso lleva metadatos de feature. Los casos sin metadatos de feature producen una puntuación idéntica a la base.
  • Las claves de puntuación de feature siguen el patrón feature_{name} (p. ej., feature_voice, feature_i18n).
  • Una compuerta de CI de cobertura de features verifica que las cinco categorías de feature tengan al menos un caso golden y que ninguna dimensión de feature devuelva una justificación malformada en todos los casos (detección de malformación). Las puntuaciones cero legítimas con justificaciones no malformadas no se marcan.

Calibración del juez (compuerta de acuerdo humano-vs-juez)

Section titled “Calibración del juez (compuerta de acuerdo humano-vs-juez)”

Un juez LLM solo es confiable en la medida en que concuerda con un experto humano. Por eso el arnés incluye una compuerta de calibración: un conjunto reservado de casos etiquetados por humanos es puntuado tanto por un experto de dominio como por el juez, y su acuerdo se mide por dimensión. La compuerta es consultiva por defecto - reporta el acuerdo y nunca bloquea un PR normal - pero en el carril de CI que exige, está armada en fail-closed sobre las dos dimensiones de seguridad, escalamiento y autolesión, de modo que un juez que se desvía del acuerdo con las etiquetas humanas en una dimensión de seguridad bloquea el carril de lanzamiento en lugar de puntuarla mal en silencio. Las dimensiones restantes (fundamentación, fidelidad, estabilidad de persona) calibran en modo consultivo. La compuerta es determinista y sin claves en CI; el punto de operación del acuerdo y el protocolo de etiquetado se calibran por despliegue y se entregan dentro del servicio contratado.

Esto cierra la brecha que la mayoría de los arneses de LLM-como-juez dejan abierta: convierte “el juez lo puntuó alto” en “el juez concuerda con nuestro experto lo suficiente como para confiar en él en las dimensiones que deciden la seguridad.”

  • Cada dimensión de evaluación la produce un evaluador nombrado detrás de un único Protocol Scorer, de modo que los evaluadores pueden cambiarse o actualizarse de forma independiente
  • La compuerta del PR es lo bastante barata y determinista como para correr en cada push sin quemar las cuotas del nivel gratuito
  • El LLM-como-juez se mantiene nocturno y usa un Claude Haiku fijado, el modelo de Anthropic de menor costo por token que aún puntúa bien en las rúbricas de tono / empatía
  • Phoenix autoalojado da un backend OTel real sin presión de cuota; su licencia ELv2 es aceptable para este caso de uso
  • La suite OWASP LLM Top 10 de Promptfoo cubre una superficie de red-team que DeepEval no cubre, fijada a un catálogo público de ataques
  • El arnés es portable: sin lock-in de SaaS, cada dependencia es de código abierto
  • El juez se calibra contra etiquetas humanas: una compuerta de acuerdo por dimensión bloquea el carril de lanzamiento si el juez se desvía del acuerdo en una dimensión de seguridad (escalamiento o autolesión)
  • Tres bibliotecas de evaluación externas significan tres vías de actualización; lo mitigamos fijando versiones menores
  • El núcleo hecho a mano es código real que mantenemos; gana su lugar al darnos control total sobre los umbrales y el formato del informe
  • Las llamadas al juez Anthropic Haiku se facturan; la cadencia nocturna más un tope pequeño de tokens las mantienen dentro del sobre de $0/mes
  • El arnés emite dos artefactos por corrida, un informe JSON legible por máquina y un resumen en Markdown
  • Inspect AI queda reservado como una tarea opcional de evaluación de capacidades; el hito inicial no depende de él
  • Phoenix y Promptfoo corren en perfiles de Docker, no en el archivo principal de Compose, para mantener pequeña la imagen de la demo en vivo

Núcleo pytest hecho a mano + DeepEval + un juez de Anthropic + Promptfoo + Phoenix

Section titled “Núcleo pytest hecho a mano + DeepEval + un juez de Anthropic + Promptfoo + Phoenix”
  • Buena, porque cada pieza es la mejor de su clase para su porción (métrica de alucinación / juez con puntuación por rúbrica / backend OTel / red-team)
  • Buena, porque pytest ya es el arnés de pruebas del proyecto
  • Buena, porque cada evaluador es intercambiable detrás de un Protocol
  • Mala, porque hay que mantener varias piezas móviles

Un SaaS de un proveedor (Braintrust / Galileo / LangSmith Eval)

Section titled “Un SaaS de un proveedor (Braintrust / Galileo / LangSmith Eval)”
  • Buena, porque la historia del dashboard es excelente de fábrica
  • Mala, porque el proyecto debe correr con cero cuentas
  • Mala, porque las definiciones de evaluación viven en la interfaz de otro
  • Buena, porque la métrica de alucinación de DeepEval es sólida y está bien soportada
  • Mala, porque no cubre por sí sola las dimensiones del juez con puntuación por rúbrica (fundamentación, fidelidad, tono) ni la superficie de red-team de Promptfoo
  • Buena, porque el formato es bien conocido
  • Mala, porque el runner es centrado en OpenAI y no se mapea limpiamente a las evaluaciones de agentes multi-turno