En peticiones de entre 500.000 y un millón de tokens, la mediana del tiempo hasta el primer token baja en torno a un 35 %. Es la cifra que Anthropic da para Message Threads, una función de la Messages API en beta pública desde el 2 de noviembre de 2026: el cliente manda la conversación completa una vez y, a partir de ahí, solo lo nuevo de cada turno. El precio por token no cambia, porque Claude sigue leyendo todo el historial; lo que desaparece es subir, validar y tokenizar otra vez la conversación entera en cada petición.
Qué cambia
Hasta ahora, la Messages API no guarda estado: cada turno de un agente reenvía el system, las herramientas y todos los mensajes y resultados de herramientas anteriores. En un agente de código con cientos de llamadas por sesión, eso supone cientos de miles de tokens viajando una y otra vez antes de que el modelo empiece a responder.
Con un hilo, la primera petición lleva la conversación completa y el campo "thread": {"type": "create"}. Las siguientes solo llevan los mensajes nuevos y "thread": {"type": "continue", "previous_message_id": "<id>"}, el id de la respuesta anterior. El servidor reconstruye la conversación antes de llamar al modelo. Anthropic dice que el hilo se guarda cifrado en memoria y no se escribe en disco, y que caduca a los 5 minutos de la última petición (se borra, como mucho, una hora después).
Está disponible en la API de Claude, en Claude Platform on AWS, en Microsoft Foundry y en Claude Models on Google Cloud (gestionado por Anthropic), para todos los modelos, con la cabecera beta message-threads-2026-08-12. Precios y límites de uso no cambian. Según el anuncio, ya va activado por defecto para la mayoría de usuarios de Claude Code, y de ahí sale el 35 %.
Cómo activarlo
El SDK trae un helper que crea el hilo en el primer turno, añade la cabecera beta, omite system y tools en los siguientes y vuelve a enviar la conversación entera cuando el hilo ya no existe:
import anthropic
client = anthropic.Anthropic()
# The helper sends nothing until the first turn
thread = client.beta.messages.thread(
model="claude-opus-5-5",
max_tokens=1024,
cache_control={"type": "ephemeral"},
system="You are a support agent for Acme. Keep replies short.",
)
thread.send({"role": "user", "content": "Hi! I have a question about an order."})
second = thread.send({"role": "user", "content": "How long does standard shipping take?"})El cache_control de primer nivel es opcional, pero un hilo no cachea por sí solo: sin breakpoints de caché, cada turno envía menos datos, pero el modelo no reutiliza nada de la caché de prompts. Si construyes las peticiones a mano, tienes que mandar la cabecera beta en todas.
Frente a previous_response_id de OpenAI
OpenAI resolvió lo mismo hace tiempo en su Responses API, con otra filosofía de almacenamiento:
| Message Threads (Anthropic) | previous_response_id (OpenAI) | |
|---|---|---|
| Dónde vive el estado | En memoria, cifrado, sin disco | Objetos de respuesta guardados 30 días por defecto (store: false lo desactiva) |
| Caducidad | 5 min sin peticiones; borrado en ≤ 1 h | 30 días |
| Bifurcar | No: solo se añade y cada id se continúa una vez | Sí, desde cualquier respuesta disponible |
| Tokens facturados | Toda la conversación, como siempre | Todos los tokens de entrada previos de la cadena |
| ZDR | No es elegible | — |
El diseño de Anthropic es deliberadamente efímero: sirve para quitar latencia a un bucle de agente activo, no para guardar la conversación. Por eso la documentación insiste en que tu aplicación sigue siendo la fuente de verdad: guarda tu copia de cada mensaje y programa desde el primer día el camino de reenvío completo.
Trampas y casos límite
systemytoolssolo en la creación. Enviarlos en uncontinue, aunque sea connull, devuelve 400.model,thinking,tool_choice,output_configo elcache_controlde primer nivel tienen que repetirse idénticos en cada turno; si cambian, errorthread_fingerprint_mismatch. Para cambiar cualquiera, hilo nuevo.- El 404 es parte del flujo.
thread_not_foundllega si el hilo caducó, si la respuesta anterior la escribió un modelo de fallback, si cambias de clave o de workspace o si la API no guardó el turno (por ejemplo, una llamada a herramienta cortada pormax_tokens). La respuesta no dice el motivo: reenvía la conversación completa en uncreate. - Lo que no admite: Message Batches, conteo de tokens, compactación bajo demanda, la mayor parte de context editing y organizaciones con HIPAA o Inference hooks activados. Como mucho 4 breakpoints de
cache_controlpor petición, y no hay API para listar, leer ni borrar hilos. - Streaming: el id llega en
message_start, pero solo se puede continuar trasmessage_stop. Tras unstop_reason: "refusal"no se continúa: hay que abrir un hilo nuevo sin ese turno.
El límite que más pesa es el de cumplimiento: si tu organización trabaja con zero data retention, esta función queda fuera, porque la conversación pasa hasta una hora en memoria del proveedor. Para el resto, en agentes de contexto largo es un cambio de pocas líneas con el helper del SDK, siempre que el camino de reenvío esté probado antes de que lo necesites.
Fuentes
- Make long-running agents faster with message threads (Anthropic, 2 de noviembre de 2026)
- Message threads, documentación (Claude Platform Docs)
- Anthropic's Message Threads cut time to first token by 35 percent (The Decoder, 3 de noviembre de 2026)
- Conversation state (OpenAI)