Ir al contenido.

English · Español · Français

Mohammad Hijjawi · septiembre de 2026, actualizado en octubre de 2026 · since-cutoff en GitHub

Tu modelo de IA para programar aprendió tus bibliotecas antes de que cambiaran. Claude Opus 4.6 en un único proyecto de ejemplo, medido con since-cutoff 0.1.0: en 7 de 16 cambios de API sondeados usó un nombre o un parámetro que ya se había eliminado; con las notas, los aciertos en 20 tareas reservadas pasaron del 5 % al 65 %. Pruébalo: uvx since-cutoff scan (sin llamadas al modelo, sin clave de API).

since-cutoff es una herramienta de línea de comandos de código abierto y un servidor MCP para proyectos de Python escritos con agentes de programación. scan muestra en qué lugares de tu código se usa una API de una dependencia que cambió después de la fecha de corte de entrenamiento del modelo, con una nota para cada una redactada a partir del diff de la API (la versión que fijas frente a la versión de comparación, la más reciente publicada al menos 30 días antes de la fecha de corte); sync escribe las notas en AGENTS.md o CLAUDE.md y las mantiene al día con tu lockfile; status, los hooks de pre-commit y una GitHub Action te avisan cuando se quedan atrás; el servidor MCP permite a un agente preguntar qué cambió en una biblioteca antes de escribir código. Solo run, opcional, llama a un modelo: mide en cuáles de los cambios se equivoca y si las notas ayudan. Cada nota lleva una etiqueta que dice qué se comprobó: redactada a partir del diff de la API, o escrita por el modelo y conservada solo si su ejemplo pasa el verificador de tipos para tu versión.

# las API modificadas que usa tu código, con una nota para cada una (sin llamadas al modelo, sin clave de API)
uvx since-cutoff scan

# escribir las notas en AGENTS.md y mantenerlas al día (sin llamadas al modelo)
uvx since-cutoff sync

# opcional: medir en qué cambios se equivoca el modelo y probar las notas (llama al modelo;
# --with añade el comprobador de tipos basedpyright, que solo necesita run)
uvx --with basedpyright since-cutoff run

pip install since-cutoff lo instala todo menos el comprobador de tipos de run; pip install "since-cutoff[run]" lo añade (basedpyright, con el Node.js que trae).

Código fuente y documentación en GitHub · PyPI · Cómo funciona, en detalle (en inglés) · Solución de problemas (en inglés)

Qué hace, a partir de la 0.6

Sigue siendo solo para Python, y las notas siguen saliendo de un diff estático de dos versiones: dicen qué cambió, no qué sabe el modelo. Los cambios de comportamiento que mantienen la misma firma no se ven.

El resto de esta página cuenta cómo surgió la herramienta y presenta las primeras mediciones, hechas con since-cutoff 0.1.0 en septiembre de 2026. Mediciones más recientes (en inglés): Lo que tu modelo no ha visto (36 bibliotecas, 21 modelos, sin llamadas al modelo, repetido con la 0.6) y el benchmark con un agente de programación (360 sesiones de Claude Code, con las notas de la 0.4.1).


Todo modelo de IA para programar tiene una fecha de corte de entrenamiento. Tu lockfile no. Cuando una biblioteca cambia su API pública después de esa fecha, un modelo que aprendió la versión anterior sigue escribiendo las llamadas antiguas, y nada en el prompt le indica lo contrario.

Quería una cifra en lugar de una anécdota: en un proyecto real, ¿con cuáles de las versiones exactas de dependencias que fija se equivoca el modelo, y basta una nota breve para corregir el error? since-cutoff es la herramienta que construí para responder a esa pregunta.

El experimento

El proyecto de ejemplo (examples/agent-app) es una pequeña aplicación basada en agentes con nueve dependencias. Seis están fijadas en versiones actuales (anthropic 1.8.0, openai 3.19.2, huggingface-hub 2.0.0, langchain-core 1.6.5, langgraph 1.2.12 y pydantic 2.13.5); las otras tres no están fijadas (fastapi, requests y httpx), así que la herramienta usa su versión más reciente.

Se evaluaron dos modelos: Claude Haiku 4.5 (fecha de corte de entrenamiento: febrero de 2025) y Claude Opus 4.6 (mayo de 2025). Las tareas y las notas las escribió Claude Opus 4.6.

Cómo mide

  1. Qué cambió. Para cada dependencia, se toma la versión de comparación, la versión más reciente publicada al menos 30 días antes de la fecha de corte de entrenamiento del modelo (por defecto; las ejecuciones con la 0.1.0 de más abajo tomaron la más reciente publicada en la fecha de corte o antes), y se compara su API pública con la versión fijada, de forma estática (con griffe, sin importar ningún módulo del paquete). Así se detectan objetos eliminados o movidos, parámetros eliminados o que pasan a ser obligatorios, parámetros que pasan a ser solo de palabra clave o solo posicionales, y nuevas marcas de obsolescencia. Para este proyecto y la fecha de corte de Claude Haiku 4.5, cambiaron 7 de las 9 dependencias; el diff de la 0.6, que compara desde el 29 de enero de 2025, señala 344 cambios incompatibles y 48 obsolescencias nuevas en API públicas, y 168 cambios en API internas.
  2. Tareas que requieren el cambio. Para los cambios de mayor prioridad, un modelo redactor de tareas genera tareas de programación breves y realistas que requieren la funcionalidad modificada, pero sin nombrar nunca el identificador que cambió ni su sustituto. Una tarea es el sondeo; las otras dos se reservan (held-out).
  3. Respuestas sin nada que consultar. El modelo recibe la tarea y el número de la versión fijada, sin herramientas, sin web y sin archivos del proyecto.
  4. Puntuación con un verificador de tipos, dos veces. La respuesta se verifica con basedpyright frente a la versión de comparación (la del paso 1) y frente a la versión fijada, cada una en un entorno aislado con sus propias dependencias. Solo cuentan los errores de conocimiento de la API (nombres, importaciones y parámetros desconocidos, argumentos que faltan, aridad), nunca los avisos del modo estricto de tipado.
    • stale: válida para la versión de comparación, inválida para la fijada
    • wrong: inválida, y no se explica por el cambio de versión
    • deprecated: válida, pero usa una API marcada con @deprecated en la versión fijada
  5. Escribir y probar las notas. Para cada fallo se escribe una nota de una línea para AGENTS.md. Una nota escrita por el modelo solo se conserva si su ejemplo pasa la verificación de tipos con la versión fijada y si todas las API que recomienda aparecen en ese ejemplo; si no, la nota es una descripción del cambio tomada directamente del diff de la API. Después, las tareas reservadas se responden de nuevo, sin las notas y con ellas, y se comparan por pares.

Nunca se ejecuta el código generado.

Resultados

Estas ejecuciones se hicieron con since-cutoff 0.1.0 y en un único proyecto, el descrito arriba.

  Claude Haiku 4.5 Claude Opus 4.6
fecha de corte de entrenamiento febrero de 2025 mayo de 2025
cambios de API sondeados 20 16
stale / wrong / deprecated / correct 5 / 1 / 2 / 12 7 / 0 / 3 / 6
bibliotecas con uso desactualizado 3 de 5 sondeadas 2 de 4 sondeadas
notas escritas (con un ejemplo que pasa el verificador de tipos) 8 (7), unos 391 tokens 10 (7), unos 437 tokens
aciertos en tareas reservadas, sin -> con notas 14% -> 57% (14 pares) 5% -> 65% (20 pares)
API que el modelo ya usaba bien, con las notas 6/6 siguen bien 6/6 siguen bien

En esta muestra, el modelo más potente no resultó más fiable. Opus 4.6 tiene una fecha de corte posterior y, aun así, escribió código desactualizado con más frecuencia: anthropic.HUMAN_PROMPT con client.completions, hf_hub_download(force_filename=...), resume_download=....

Más código desactualizado de la ejecución con Haiku, en cada caso válido para la versión de comparación y rechazado por el verificador de tipos en la fijada:

¿Lo corrige una nota?

since-cutoff escribió 8 notas, unos 391 tokens, 7 de ellas con un ejemplo que pasa el verificador de tipos (en un caso se recurrió a una simple afirmación extraída del diff de la API). Por ejemplo:

**anthropic 1.8.0**
- `temperature=...` was removed from `messages.create()` in anthropic 1.8.0. Omit the `temperature` parameter entirely; there is no replacement.

**openai 3.19.2**
- `client.beta.vector_stores` is removed in openai 3.19.2. Use `client.vector_stores` instead.

En las tareas reservadas de los cambios en los que había fallado, el modelo acertó en el 14 % sin las notas y en el 57 % con ellas (14 tareas emparejadas de 7 cambios de API). La tarjeta de la ejecución también indica «4 of 7 changes fixed, 95% CI 25-84%»: es el recuento de la versión 0.1.0, que también contaba un cambio como corregido cuando una respuesta reservada ya era correcta sin las notas, y el intervalo corresponde a ese recuento, no a las dos tasas. El modelo siguió usando bien, con las notas en su contexto, las seis API que ya acertaba.

Qué dicen y qué no dicen estas cifras

Por qué me importa

Esto surgió de un artículo que coescribí para EMNLP 2026 sobre el aislamiento temporal (temporal isolation): usar la fecha de corte de entrenamiento de un modelo como experimento natural sobre lo que sabe. Las nuevas versiones de las bibliotecas son el mismo experimento, con una utilidad muy práctica: la respuesta es una lista de líneas para poner en AGENTS.md.

Pruébalo

# las API modificadas que usa tu código, con una nota para cada una (sin llamadas al modelo)
uvx since-cutoff scan

# escribir las notas en AGENTS.md y mantenerlas al día (sin llamadas al modelo)
uvx since-cutoff sync

# opcional: medir en qué cambios se equivoca el modelo y probar las notas (llama al modelo;
# --with añade el comprobador de tipos basedpyright, que solo necesita run)
uvx --with basedpyright since-cutoff run

run funciona con Claude Code (como plugin), Anthropic, OpenAI, OpenRouter, DeepSeek, Ollama y cualquier servidor compatible con OpenAI; scan, sync y status solo necesitan la fecha de corte del modelo. sync --profile evaluated escribe las notas como las midió el benchmark (el alcance importado, hasta 5 API por paquete), y sync --header-only solo su encabezado: los paquetes modificados y sus versiones. since-cutoff status (sin conexión), sync --check, los hooks de pre-commit y una GitHub Action avisan cuando las notas se quedan atrás; since-cutoff mcp permite a cualquier cliente MCP (Claude Code, Codex, Cursor, VS Code, Gemini CLI) consultar los cambios de una biblioteca antes de escribir código. Por ahora solo admite Python; TypeScript es lo siguiente. Los comentarios sobre el método son muy bienvenidos en los issues, y los resultados de tus propios proyectos, en Share your results («Comparte tus resultados», en inglés). Si quieres contribuir con código, los good first issues son un buen punto de partida.