Creen tres archivos de especificaciones antes de darle trabajo a Claude Code o Codex
Después de un año de desarrollo asistido por agentes de IA, descubrí que los archivos de especificaciones estructurados resolvían el problema de inconsistencia mucho mejor que cualquier técnica de prompting.
El mismo task, dos sesiones distintas, dos resultados completamente diferentes. Una vez Claude Code refactorizó un módulo respetando los patrones del proyecto, actualizó los tests y dejó todo limpio. La siguiente vez ignoró los tipos existentes, inventó nombres de funciones que no existían en ningún lado, y rompió tres archivos de configuración que no tenía por qué tocar.
No cambié el modelo. No cambié el prompt. Lo único que cambió fue que en la segunda sesión empecé sin contexto estructurado.
Tardé varios meses en darme cuenta de que el problema no era el agente sino lo que yo le estaba entregando al inicio de cada sesión.
El problema de fondo no es el modelo
Cuando los resultados son inconsistentes, la reacción natural es ajustar el prompt. Se agrega más detalle, se reformula, se experimenta con distintas formas de pedir lo mismo. Yo hice exactamente eso durante semanas. Funcionaba a veces, pero no de forma predecible.
El problema real es más simple: los agentes de IA no tienen un modelo mental persistente de tu proyecto. Cada sesión empieza desde cero. Sin estructura explícita, el agente infiere el contexto a partir del código que puede ver, y esa inferencia puede ser correcta o completamente equivocada dependiendo de qué archivos lea primero.
Lo que faltaba no era un prompt mejor. Eran tres capas de intención documentada que el agente pudiera leer antes de escribir una sola línea de código.
La investigación sobre instrucciones que se contradicen
Antes de describir las tres capas, vale la pena mencionar por qué la estructura importa tanto.
Investigadores del MIT y Stanford publicaron en 2024 un estudio sobre lo que llamaron la “Curse of Instructions”: cuando los modelos reciben instrucciones que se contradicen o que están mezcladas sin jerarquía clara, su comportamiento se vuelve impredecible de maneras que no se pueden anticipar solo observando los outputs. El modelo no reporta la contradicción; simplemente elige una interpretación y la sigue con aparente confianza.
En la práctica, esto significa que un CLAUDE.md genérico más un prompt largo más el código del proyecto pueden contener docenas de señales contradictorias sobre convenciones de nombres, manejo de errores o estructura de archivos. El agente las resuelve de alguna manera, pero no de la manera que ustedes esperan.
La solución que encontré funciona porque separa esas señales en capas con responsabilidades distintas.
Capa 1: CLAUDE.md como constitución del proyecto
CLAUDE.md es el archivo que Claude Code lee automáticamente al inicio de cada sesión. La mayoría de los equipos lo usan para poner instrucciones operativas: qué comandos existen, qué herramientas usar, qué directorios no tocar. Eso está bien, pero se quedan cortos.
Lo que debería contener es la constitución del proyecto: las decisiones que ya se tomaron y que no están abiertas a reinterpretación.
En uno de mis proyectos el archivo tiene tres secciones: decisiones de arquitectura con su razón (no solo “usamos Zod”, sino “usamos Zod porque los tipos en runtime son obligatorios para este caso de uso”), patrones de código que el agente debe seguir con ejemplos cortos, y una lista de lo que explícitamente no se hace aunque parezca razonable.
Esa última sección es la que más ayuda. Hay patrones que un agente sugiere de forma natural porque son correctos en contextos genéricos, pero incorrectos para un proyecto específico. Documentarlos previene que el agente los proponga en cada sesión.
Lo que no funciona es poner en CLAUDE.md instrucciones sobre tareas específicas. Si el archivo crece más de 300 líneas intentando anticipar todos los escenarios posibles, se convierte en ruido y el agente empieza a ignorar secciones. Probé esto con un archivo de 600 líneas y los resultados fueron peores que con uno de 80. El límite existe; no lo probé formalmente, pero 150-250 líneas parece ser el rango donde la adherencia se mantiene alta.
Capa 2: SPEC.md como descripción de qué y por qué
SPEC.md describe lo que se va a construir, no cómo. La distinción importa porque los agentes son buenos resolviendo problemas técnicos concretos, pero malos eligiendo qué problema resolver si hay ambigüedad.
Un SPEC.md útil tiene cinco secciones: el objetivo en una oración, el contexto del usuario (quién va a usar esto y en qué situación), los criterios de éxito medibles, las restricciones no negociables, y los casos límite conocidos.
La sección de casos límite es la que más trabajo cuesta escribir y la que más valor aporta. Obliga a pensar en situaciones que el agente va a encontrar y que podrían resolverse de varias maneras. “¿Qué pasa si el usuario envía un formulario con campos vacíos?” debería tener una respuesta explícita antes de que el agente empiece a codear, no después.
Una práctica que mejoró significativamente la calidad de mis SPEC.md fue lo que llamo “entrevistar al agente” antes de escribir el plan de implementación. Le presento el spec incompleto y le pregunto qué información le falta para completar la tarea. Las preguntas que hace revelan ambigüedades que yo no había notado. En tres de cada cuatro veces, al menos una de esas preguntas cambia alguna decisión de diseño.
Capa 3: plan.md como secuencia de trabajo atómico
El plan de implementación es la capa más táctica. Su propósito es dividir el trabajo en tareas que cumplan tres condiciones: son verificables de forma independiente, tienen rutas de archivo explícitas, y duran entre dos y cinco minutos de ejecución del agente.
Esa duración específica importa. Tareas muy cortas fragmentan el trabajo de una manera que hace difícil mantener coherencia entre pasos. Tareas muy largas acumulan demasiada incertidumbre y cuando algo sale mal es difícil saber en qué punto ocurrió.
Cada tarea en el plan debería tener esta forma: qué archivo se modifica, qué comportamiento debe tener después del cambio, y cuál es el test que confirma que el cambio es correcto. Esto último es importante. Si se escribe el plan antes de escribir el código, naturalmente se terminan definiendo los tests primero, lo que resuelve de forma casi accidental el problema de cobertura de tests.
Un ejemplo de tarea bien definida:
Tarea 3: Agregar validación de email en src/lib/validators.ts
- Función: validateEmail(input: string): ValidationResult
- Behavior: retorna { valid: false, reason: "formato inválido" } si el string no tiene @ y dominio
- Test: src/lib/validators.test.ts > describe("validateEmail") > case "rechaza strings sin @"
Una tarea mal definida: “Implementar validación de formulario.”
Cuándo dividir en sesiones separadas
Una de las cosas que tardé más en aprender es que un contexto de sesión largo no es mejor que uno corto bien estructurado. Después de cierto punto, el agente empieza a perder consistencia con las decisiones que tomó al principio de la sesión.
La regla que uso es dividir en sesiones nuevas cuando: se completa un componente vertical completo (desde el modelo hasta el endpoint), cuando el plan tiene más de ocho tareas, o cuando la sesión ha producido más de diez archivos modificados. Al inicio de cada sesión nueva, el agente recibe CLAUDE.md, el SPEC.md actualizado, y solo la parte del plan que corresponde a esa sesión.
Esto suena a más trabajo administrativo, y al principio lo es. Pero una sesión de dos horas con contexto limpio produce resultados más consistentes que una sesión de cinco horas donde el agente acumula contexto degradado.
Un modelo de madurez informal
Después de trabajar con varios equipos que están adoptando agentes de IA, noté tres patrones recurrentes.
Nivel 1: el equipo usa los agentes sin estructura de contexto. Los resultados son impredecibles. Los buenos resultados se atribuyen al modelo, los malos al prompt. Se invierte tiempo en prompt engineering sin que mejore la consistencia.
Nivel 2: el equipo tiene un CLAUDE.md bien mantenido. Los resultados mejoran para tareas rutinarias pero siguen siendo inconsistentes para trabajo nuevo. Falta la especificación de intención por tarea.
Nivel 3: el equipo mantiene las tres capas y las actualiza como parte del proceso de desarrollo. CLAUDE.md se actualiza cuando cambian decisiones de arquitectura. SPEC.md se escribe antes de empezar cualquier feature nueva. El plan se construye con tareas atómicas verificables. En este nivel, los agentes producen código que pasa code review en el primer intento con mucha más frecuencia.
La mayoría de los equipos que conozco están entre Nivel 1 y Nivel 2. El salto al Nivel 3 no requiere herramientas nuevas ni cambios en el modelo que usan. Requiere tratar la documentación de intención como parte del trabajo, no como algo que se hace después.
Por dónde empezar hoy
Si tienen un proyecto activo donde ya usan Claude Code o Codex, el camino más corto es este: abran el proyecto y escriban un CLAUDE.md de 100 líneas con las tres o cuatro decisiones de arquitectura más importantes y los dos o tres patrones que el agente debería seguir siempre. No intenten ser exhaustivos. Comiencen con lo que ya saben que el agente hace mal.
La próxima vez que inicien una sesión con esa base, la diferencia en consistencia va a ser visible en los primeros diez minutos.
Unite al boletín
Recibí actualizaciones sobre mis últimos proyectos, artículos y experimentos con IA y desarrollo web.