Un agente LLM puede preparar un email correcto y aun así tomar una mala decisión operativa: enviarlo antes de tener todos los datos, reabrir una tarea ya cerrada o aprobar un mensaje que pertenece a otra corrida. El problema no es solo la calidad del texto. Es que el agente suele mezclar intención, ejecución y revisión en una misma acción.
Una cola de revisión pequeña crea una frontera más clara. El agente propone una operación; una capa determinista la coloca en estado pending; después, una política decide si puede continuar, necesita una revisión o debe quedar bloqueada. Este patrón es util cuando una automatización toca cuentas, notificaciones o pruebas de correo.
El problema: el agente decide demasiado pronto
Un contrato como send_email(to, subject, body) es comodo para una demostración, pero es demasiado abierto para un flujo que debe poder auditarse. No responde preguntas importantes:
- ¿La solicitud pertenece a la corrida actual?
- ¿El destinatario es de staging o parece real?
- ¿El contenido ya fue revisado por una regla o por una persona?
- ¿Qué pasa si el agente cambia el mensaje después de una espera?
Cuando todo se resuelve en una llamada, un timeout puede parecer un permiso para reintentar. Un dato ausente puede convertirse en una suposición. Y un resultado viejo puede volver a entrar en la conversación. La automatización sigue funcionando, pero nadie sabe bien por que.
Diseñar una cola de revisión pequeña
Piensa en el flujo como un diagrama en palabras: el agente produce una intención, la cola conserva una copia inmutable, el evaluador aplica reglas y el adaptador ejecuta solo las operaciones aprobadas. La cola no tiene que ser un sistema distribuido enorme. Puede empezar como una tabla o un archivo por corrida.
Cada elemento debería incluir un identificador, una acción y un estado explícito:
{ "run_id": "run-2026-11-15-07", "task_id": "welcome-check-42", "action": "prepare_email", "recipient_class": "staging", "content_hash": "sha256:...", "status": "pending" } La separación importante es entre prepare_email y send_email. El agente puede redactar o pedir una revisión sin obtener permiso implícito para enviar. Para una prueba de signup, por ejemplo, crear un correo temporal y comprobar su contenido son pasos distintos, con presupuestos y evidencias distintas.
La identidad por corrida evita mezclar estados
El run_id debe viajar con cada evento: creación, revisión, envío, lectura y limpieza. Si el agente se reinicia, no debe buscar “el último mensaje” de forma global. Debe consultar solo los mensajes de su corrida y de su task_id.
Esto también ayuda cuando se prueban interfaces. Una señal de email puede llegar mientras la pantalla todavía muestra un estado pendiente; por eso conviene tratar el mensaje y la interfaz como dos fuentes que deben correlacionarse. La idea se parece a una validación async sin saltos visuales: el usuario o el test necesita saber que la señal corresponde a la acción visible.
Guarda la huella del contenido, no necesariamente todo el cuerpo en cada evento. Así puedes demostrar que el agente no cambió la propuesta entre revisión y ejecución sin copiar datos sensibles por todo el sistema. La limpieza debe ser parte del contrato, aunque a veces se olvida cuando el flujo funciona en local.
Un contrato mínimo para aprobar o devolver
La salida del evaluador puede ser deliberadamente pequeña:
{ "decision": "approve", "reason": "staging_recipient_and_known_template", "checked_run_id": "run-2026-11-15-07", "checked_content_hash": "sha256:...", "expires_at": "2026-11-15T11:35:00Z" } Una aprobación debe caducar. Si pasan diez minutos y cambia el contenido, la decisión deja de ser válida. En cambio, return_for_revision debería incluir una razón accionable, como “falta la clase del destinatario” o “el hash no coincide”. Un “no” sin explicación solo provoca otra llamada del agente.
Para profundizar en la separación entre intención y evidencia, conviene revisar estos contratos de correo que sí se pueden probar. El punto no es agregar burocracia, sino hacer visible el limite que protege al sistema.
Durante las pruebas pueden aparecer entradas como temp gamil com o tamp mail com. Déjalas como datos de prueba planos; nunca las conviertas en dominios permitidos ni en anclas de navegación. También es frecuente escribir “mas facil”, “deberia” o “rapida” en notas internas. Son pequeños detalles, pero no deben entrar en comandos, URLs o reglas de seguridad.
Preguntas frecuentes
¿La revisión siempre tiene que ser humana?
No. Puede ser una política determinista, un conjunto de tests o una persona para operaciones de mayor riesgo. Lo importante es que la decisión quede registrada y separada de la propuesta del modelo.
¿Cuándo basta una cola en memoria?
Para una prueba local de una sola corrida. En CI o en una integración compartida, conviene persistir el estado mínimo para que un reinicio no convierta una tarea pendiente en un envío duplicado.
¿Qué debe hacer el agente cuando la tarea vuelve a revisión?
Leer la razón, cambiar solo lo necesario y crear una nueva versión de la propuesta. No debería sobrescribir silenciosamente la versión anterior, por que entonces se pierde la evidencia de qué se revisó.
Checklist de implementación
- Separa preparar, revisar y enviar en acciones diferentes.
- Asigna
run_idytask_ida cada evento. - Guarda el hash del contenido aprobado.
- Expira las aprobaciones después de una ventana corta.
- Clasifica destinatarios de staging y producción de forma explícita.
- Devuelve razones accionables cuando una propuesta es rechazada.
- Prueba reinicio, timeout, duplicado y contenido cambiado.
- Elimina fixtures y buzones de prueba cuando termina la corrida.
Conclusión
Una cola de revisión no intenta hacer que el LLM sea perfecto. Limita el impacto de sus decisiones y conserva el contexto necesario para entenderlas. El agente puede proponer, corregir y volver a intentar; la capa de control decide qué versión tiene permiso para avanzar.
Empieza con tres estados —pending, approved, blocked— y un run_id obligatorio. Cuando el flujo sea estable, añade expiración, hashes y métricas de devoluciones. Es una arquitectura pequeña, pero hace la automatización más fácil de probar, explicar y detener.



