Un CLI agéntico por dentro: bucles, contexto y permisos
Qué hace funcionar a un CLI de programación agéntico: bucles de llamadas a herramientas, gestión de contexto, permisos y diseño cliente/servidor.

El modelo es la parte fácil. Esa es la tesis, al menos, y tras ver surgir, bifurcarse y tropezar a una docena de CLI agénticos de programación en los últimos dos años, creo que es cierta: un CLI agéntico de programación triunfa o fracasa por su arnés, no por su modelo. El lanzamiento de OpenCode 2.0 (un agente de programación de código abierto para la terminal que ganó mucha tracción esta semana) es una buena excusa para decirlo en voz alta. Lo interesante de esa versión no son nuevas integraciones de modelos. Son una separación cliente/servidor, plugins con recarga en caliente, tareas que pueden ejecutarse en segundo plano y un bucle del agente rediseñado. Fontanería, en otras palabras. La fontanería es el producto.
Soy un ex ingeniero de ML, así que esta conclusión me molestó. Quería que la calidad del modelo fuera el factor diferencial. Pero cuando miro por qué sigo usando o abandono estas herramientas, la respuesta nunca es «el modelo se volvió más listo». Es «la herramienta dejó de pedirme que aprobara cada comando», o «por fin recarga mi configuración sin reiniciar», o «puedo conectar una GUI a una sesión que corre en una máquina remota». Vamos a desmontar los tres subsistemas que de verdad determinan si un agente de programación es útil: el bucle de llamadas a herramientas, la gestión del contexto y el modelo de permisos. Después reconoceré dónde se rompe la tesis contraria.
El bucle de llamadas a herramientas es un sistema distribuido
Quitando el marketing, todos los agentes de programación son el mismo programa: llamar al modelo con un prompt y una lista de herramientas, recibir texto o una llamada a una herramienta, ejecutar la herramienta, añadir el resultado y repetir. Suena trivial. No lo es, y las herramientas que lo tratan como trivial resultan chapuceras en cinco minutos de uso real.
Piensa en lo que el bucle tiene que manejar de verdad. Las ejecuciones de herramientas fallan: el compilador da errores, la suite de tests se cuelga, el archivo no existe en esa ruta porque el modelo lo inventó. El modelo genera JSON mal formado para los argumentos de sus herramientas. Una llamada tarda cuarenta segundos y el usuario pulsa Escape a mitad de ejecución. Llegan dos llamadas en un mismo turno y una de ellas no debe ejecutarse si falla la otra. La ventana de contexto se llena a mitad de la tarea y algo tiene que ceder. Todo esto es un problema de concurrencia y fallos, no de inteligencia. Ya he defendido que los agentes LLM son simplemente sistemas distribuidos, y el CLI de programación es el ejemplo más puro: tienes un componente remoto poco fiable y no determinista (el modelo) coordinándose con componentes locales con efectos (shell, sistema de archivos, LSP), y el bucle es el protocolo de consenso entre ellos.
Por eso importa que OpenCode 2.0 haya reconstruido, según se informa, su bucle sobre Effect, un framework de TypeScript para concurrencia estructurada y errores tipados. Esa elección indica que el equipo dejó de pensar en el bucle como «un while con un fetch dentro» y empezó a tratarlo como lo que es: un sistema de efectos interrumpibles, componibles y reintentables, con canales de error explícitos. Cuando tu bucle de agente tiene semántica de cancelación real, «el usuario pulsa Escape» se convierte en un evento de primera clase en vez de un estado corrupto. Cuando los resultados de las herramientas están tipados, puedes validar la salida del modelo antes de ejecutarla, lo que encaja muy bien con técnicas como la decodificación restringida, donde limitas el espacio de salida del modelo para que las llamadas mal formadas sean imposibles y no solo detectadas.
La arquitectura cliente/servidor es la característica de la que nadie hace marketing
Una de las decisiones de diseño más relevantes de un CLI de programación es si el agente es un proceso o un servicio. El diseño ingenuo (un proceso, una terminal, y la sesión muere cuando muere la terminal) es como empezaron la mayoría de estas herramientas, y es un techo. El modelo cliente/servidor de OpenCode, donde un servidor de larga duración es dueño de las sesiones y cualquier número de clientes (TUI, app de escritorio, UI web) se conecta a él, elimina ese techo. En la práctica significa que tu sesión sobrevive a que cierres la terminal, que puedes ejecutar el agente en una máquina de desarrollo remota y controlarlo desde una app nativa en tu portátil, y que varias interfaces pueden observar la misma sesión.
Si alguna vez has intentado ejecutar un agente en una VM por SSH y una reconexión se llevó por delante la sesión, sabes que esto no es un capricho. Es la diferencia entre un juguete y una infraestructura. Los agentes de larga duración pertenecen a la misma categoría que las compilaciones y las suites de tests: cosas que lanzas, dejas correr y revisas más tarde. Las tareas en segundo plano de OpenCode 2.0 van en la misma dirección: el agente deja de ser una conversación síncrona y se convierte en un ejecutor de trabajos con interfaz de chat.
Ahora, la advertencia, porque mantengo esta opinión de forma coherente: una arquitectura de servidor no significa un demonio permanente. Varios comentaristas señalaron con recelo que todos los arneses de agentes quieren de repente un proceso en segundo plano persistente en tu máquina. Ese instinto es correcto. Ya escribí que las herramientas CLI no deberían instalar demonios en segundo plano por defecto, y lo sostengo. Hay un término medio limpio: arrancar el servidor bajo demanda, limitado al directorio del proyecto y cerrado cuando se desconecta el último cliente. Obtienes persistencia de sesión y conexión de múltiples clientes sin un proceso siempre activo enviando datos desde tu máquina. Que OpenCode cargue la configuración desde la carpeta de la sesión y no desde el directorio de trabajo del servidor (otro cambio de la 2.0) sugiere que entienden que el servidor debe seguir al proyecto, y no al revés.
La gestión del contexto es donde vive la calidad
Pregunta a cualquier practicante por qué un agente «se volvió tonto» tras una hora de trabajo y casi nunca la respuesta es una regresión del modelo. Es podredumbre de contexto. La ventana se llenó de salida de herramientas obsoleta, callejones sin salida y el texto completo de archivos que eran relevantes hace cuarenta turnos. El modelo ahora toma decisiones sobre un pajar, y la capacidad de encontrar la aguja se degrada mucho antes de que llegues al límite nominal de tokens.
Un buen arnés trata el contexto como un presupuesto con una política de asignación, no como una tubería. En concreto, eso implica varias cosas que funcionan juntas:
- Truncado de la salida de herramientas con vías de escape para recuperarla. Un log de tests de 5.000 líneas debería entrar en el contexto como sus cuarenta líneas fallidas más una nota indicando que el log completo está en una ruta que el modelo puede volver a leer. El arnés decide qué es relevante; el modelo decide cuándo necesita más.
- Subsesiones y subagentes. «Investiga cómo funciona la autenticación en este repo y dame un resumen» debería ejecutarse en un contexto aislado que devuelva un resumen, no toda la transcripción de la exploración. La mejora en la comunicación entre subsesiones de OpenCode 2.0 es exactamente esta idea.
- Compactación que preserva la intención. Cuando la ventana se llena, algo tiene que resumir la conversación hasta ese punto. Un arnés que resume de forma ingenua pierde las restricciones del usuario («no toques el módulo de facturación») junto con el ruido. Una buena compactación mantiene las decisiones y restricciones literalmente y comprime solo la narrativa.
- Configuración y skills como contexto, no como código. Las instrucciones a nivel de proyecto, las herramientas definidas por plugins y los archivos de skills consumen ventana. Recargarlos en caliente, otra corrección de la 2.0, importa porque editar el contexto de tu agente sin reiniciar su sesión es como iteras sobre el comportamiento del propio agente.
Nada de esto es inteligencia del modelo. Todo ello determina cuán inteligente parece el modelo. Un modelo de frontera con una política de contexto descuidada perderá contra un modelo más barato con una política disciplinada en cualquier tarea que dure más de veinte minutos.

Modelos de permisos: la función aburrida que decide la adopción
Aquí tienes una pregunta del debate en HN que considero la cuestión de producto más importante de este espacio: ¿existe algo entre «aprobar cada comando» y el «modo yolo»? La aprobación automática total es realmente peligrosa: un agente de programación con acceso a la shell puede ejecutar rm -rf, git push --force y filtrar tus variables de entorno en un solo turno. La aprobación manual total es realmente inutilizable: aprobar ochenta comandos por hora significa que no estás supervisando al agente, sino que eres un teclado humano lento interrumpiendo. La herramienta que acierte en el punto medio gana a los pragmáticos.
El punto medio es un modelo de permisos graduado, y su espacio de diseño se entiende mejor de lo que la gente cree:
- Solo lectura frente a escritura frente a ejecución. Leer es casi gratis; escribir debería limitarse al árbol del proyecto; la ejecución es donde más importa la política.
- Listas blancas con conciencia de argumentos.
git statusse aprueba automáticamente;git pushpide confirmación. Las herramientas ingenuas comparan el nombre del binario; las buenas comparan el verbo y las flags, porquenpm testynpm publishson el mismo binario con radios de impacto muy distintos. - Concesiones limitadas a la sesión. «Permitir siempre este comando en esta sesión» es la función de permisos con mayor valor que existe. Convierte setenta preguntas en una sola.
- Contención para lo irreversible. El acceso a la red, cualquier cosa fuera del directorio del proyecto y cualquier cosa que toque credenciales deberían estar restringidos de forma estructural, no simplemente sujetos a una pregunta.
Esta última viñeta es la parte en la que la mayoría de los arneses invierten menos, porque preguntar es fácil y contener es difícil. Pero un prompt es una pregunta que el modelo espera que contestes bien a las 6 de la tarde un viernes. Aislar el árbol de procesos del agente (red restringida, montajes de archivos acotados) hace imposibles clases enteras de fallos, independientemente de lo que haga el modelo o el usuario. He detallado el compromiso en contención frente a monitorización en agentes de IA; mi resumen es que los prompts son monitorización, el sandboxing es contención, y quieres contención para todo lo irreversible. El ecosistema de CLI está aprendiendo esto poco a poco. Los que lo aprendan más rápido ganarán la confianza que permite a los usuarios activar la aprobación automática para el 90% aburrido.
Extensibilidad y el problema de los modelos autoalojados
Dos lecciones menores de la discusión sobre la 2.0 merecen atención. Primera: «todo es un plugin» está ganando. Los usuarios construyen skills, editores de configuración y hooks de flujos de trabajo sobre estos arneses, y el arnés que hace de los plugins ciudadanos de primera clase (con recarga en caliente, capacidad de observar sesiones y de modificar el comportamiento) multiplica el esfuerzo de la comunidad en vez de competir con él. La señal de que OpenCode se toma esto en serio: su propia app de GitHub clasifica los reportes de bugs reproduciendo el problema y comentando los hallazgos, es decir, usa el agente para mantener el agente. Esa es la «autoconciencia» que elogiaron los usuarios, y es un resultado de la arquitectura de plugins, no del modelo.
Segunda: la independencia del modelo es más difícil de lo que parece, y es un problema de formato de contexto. Un usuario probó un modelo local excelente, entrenado para emitir comandos en bash, mientras el arnés esperaba obstinadamente llamadas a herramientas al estilo JavaScript, y ambos simplemente no podían interoperar. Este es el acoplamiento oculto de todo arnés: el formato de las llamadas a herramientas, las suposiciones del system prompt y la distribución de entrenamiento del modelo tienen que alinearse. Un arnés que codifica de forma fija las convenciones de una familia de modelos no es independiente del modelo, como mucho es tolerante con él. Si los modelos locales van a importar para los agentes de programación (y por coste y privacidad deberían), los arneses necesitan dialectos de llamadas a herramientas intercambiables, no solo endpoints de API intercambiables.
Dónde se rompe la tesis contraria
Dije que el modelo es la parte fácil. Toca conceder los matices. La tesis se sostiene para el diseño del arnés (bucles, contexto, permisos), pero hay lugares donde el modelo es de verdad el cuello de botella. La fiabilidad en el uso de herramientas se entrena en el propio modelo; un modelo que no puede generar llamadas a funciones válidas de forma consistente hace que cualquier arnés parezca roto, y ninguna cantidad de concurrencia estructurada basada en Effect arregla un modelo que discute con su propio esquema. La planificación de varios pasos en horizontes largos sigue separando niveles de modelos de formas que se notan dentro de una sola sesión. Y el encuadre arnés frente a modelo tiene fecha de caducidad: a medida que los modelos absorben el comportamiento agéntico en su entrenamiento (uso nativo de herramientas, planificación nativa de horizontes largos), las capacidades migran del arnés a los pesos, y la ingeniosa función de hoy se convierte en esfuerzo desperdiciado mañana. Los equipos que construyen arneses deberían asumir que están construyendo andamiaje que los modelos acabarán volviendo obsoleto. Y, sinceramente, eso es un argumento a favor de arneses de código abierto con ecosistemas de plugins, porque estos sobreviven gracias a la comunidad y no a una brecha de capacidad temporal.
También hay un suelo de UX que ninguna arquitectura justifica. Algunos usuarios probaron OpenCode 2.0 y aun así lo encontraron torpe; otros se quejaron del arranque lento y de una base de datos de historial de chat muerto que no para de crecer. No son problemas profundos, pero son los que hacen que la gente abandone una herramienta en los primeros diez minutos, antes de que el elegante bucle del agente tenga oportunidad de lucirse. El pulido también es una característica, y es la que los proyectos de código abierto suelen financiar peor.
El modelo escribe el código, pero el arnés decide si confías lo suficiente como para dejarlo actuar.
Así que mi consejo pragmático, como alguien que ha visto esta categoría cambiar sin parar: elige tu agente de programación como elegirías una base de datos, no como elegirías al ganador de un benchmark de modelos. Mira cómo gestiona los fallos el bucle, la política de contexto, la granularidad de los permisos y si las sesiones sobreviven a que cierres la terminal. Esas son las partes que seguirán importando después del próximo lanzamiento de modelo, cuando todos sean igual de listos otra vez.


