Servir varios modelos en producción: routing, versionado y canary
Tu app no necesita el modelo más caro para el 80% de las peticiones. Pero tampoco puedes hardcodear un modelo en cada archivo y esperar poder cambiarlo cuando salga uno mejor. La capa que resuelve eso es aburrida y vale oro: alias, versionado y canary.
La idea central: una capa de alias
En vez de nombrar modelos en tu código, nombras capacidades:
// Fuente: Provider & Model Management — Vercel AI SDK (adaptado)
import { customProvider, gateway } from 'ai';
export const models = customProvider({
languageModels: {
fast: gateway('anthropic/claude-haiku-4-5'),
writing: gateway('anthropic/claude-sonnet-5'),
reasoning: gateway('anthropic/claude-opus-5.5'),
},
fallbackProvider: gateway,
});
Tu código pide models.languageModel('fast') y tú cambias la versión real en un solo lugar. Cuando salga un modelo mejor, lo actualizas ahí y ya. - Source: Provider & Model Management - Vercel AI SDK
El AI SDK también permite un registro de proveedores (para mezclar varios con prefijos tipo openai:gpt-…) y middleware para preconfigurar parámetros. - Source: Provider & Model Management - Vercel AI SDK
Los 3 modos de routing
| Modo | Cómo decide | Cuándo usarlo |
|---|---|---|
| Estático | Por alias en el código (fast para clasificar, reasoning para decidir) | Siempre; es el punto de partida |
| Por política | Reglas y middleware (por usuario, feature flag, tipo de tarea) | Cuando la decisión depende del contexto de tu app |
| Por clasificador | Un modelo barato evalúa la petición y elige el modelo | Cuando "es difícil" no se puede saber por reglas |
El tercero tiene un patrón ya documentado: LangChain demostró un ModelRouterMiddleware donde un modelo clasificador (System One, como Jev) elige entre el modelo barato y el caro según criterios que tú defines. - Source: Building a Harness with Jev - Sydney Runkle / LangChain
Versionado: la disciplina que te salva
- Un alias por capacidad, nunca un modelo suelto en el código.
- Registra la versión real que hay detrás de cada alias (un comentario o una constante).
- Cambiar de versión es un cambio de configuración, no un refactor: así se puede revertir en un minuto.
- Fija versiones explícitas ("claude-sonnet-5", no "sonnet-latest") en producción; los alias móviles te cambian el comportamiento sin avisar.
Canary: cambiar con red
El canary es enviar un porcentaje del tráfico al modelo nuevo y comparar:
- 5% al nuevo durante unas horas o días.
- Compara con las evals y con métricas de producción (latencia, errores, costo por request).
- Sube al 25%, 50%, 100% solo si gana en tus evals.
- Vuelve atrás apagando el porcentaje: es una bandera, no un deploy.
Sin evals, el canary es ruido. → Evals: los 3 tipos
Los números que hacen la decisión obvia
Los precios por millón de tokens de los proveedores hacen que rutear no sea una optimización menor. Compara el mismo proveedor, tres modelos (precios de lista por MTok, entrada/salida):
| Modelo | Entrada | Salida |
|---|---|---|
| Haiku 4.5 | $1 | $5 |
| Sonnet 5 | $2 | $10 |
| Opus 5.5 | $4 | $20 |
Fuente: Pricing - Anthropic
Ese es un factor de 4x entre el más chico y el más grande del mismo proveedor (y la diferencia se multiplica con modelos de razonamiento). Si el 70% de tus peticiones son clasificar o extraer, mandarlas al modelo barato no es "ahorrar un poco": es la mitad de la factura. La comparativa completa, en El costo real de tu feature de AI.
Cómo montarlo (5 pasos)
- Define 3-4 alias por capacidad (fast, writing, reasoning) y migra tu código a ellos.
- Fija versiones explícitas por alias en producción y documenta cuál es cada uno.
- Añade routing por reglas para tus casos obvios (clasificar, extraer, resumir).
- Evalúa un clasificador para los casos grises; no antes.
- Pilota cambios con canary y decide con evals + métricas de producción.
Esto es infraestructura de serving; la decisión económica detrás está en Model routing y costos y la elección del modelo, en Elegir modelo en 2026.
¿Sirves con un solo modelo o ya tienes alias y canary? Cuéntame en los comentarios qué te frenó para no rutear antes.