Workflow SDK 5: los trabajos largos de IA necesitan un contrato de cancelación
El problema de un trabajo de IA largo no es solo la espera. El problema aparece cuando nadie puede explicar qué siguió ejecutándose después de cancelar. Un usuario cancela, pero la llamada al modelo continúa; gana un timeout, pero una subida termina igual; una cuota se excede y el retry vuelve a gastar.
El 16 de junio de 2026 Vercel anunció que Workflow SDK 5 beta soporta AbortController y AbortSignal a través de workflows y steps. Con sandboxes de hasta 24 horas, el mensaje es claro: los agentes duran más, por lo tanto deben poder detenerse mejor.
Qué cambió
Un workflow puede crear un AbortController, pasar la señal a steps y llamar abort() cuando gana un timeout, un race, un hook externo o una regla de cuota. La documentación indica que la señal sobrevive a suspensiones, replay determinista e invocaciones separadas.
La cancelación es cooperativa: el step debe pasar la señal a fetch, llamar signal.throwIfAborted(), revisar signal.aborted o escuchar el evento.
Por qué importa
OCR, generación de reportes, automatización de navegador, agentes multi-modelo y pruebas E2E necesitan ejecuciones largas. Sin contrato de cancelación, aparecen tokens desperdiciados, APIs llamadas de más y estados ambiguos.
Las preguntas de comunidad sobre producción y cleanup muestran que el punto difícil es operativo.
Impacto operativo
Los timeouts se vuelven política de producto. Los trabajos paralelos pueden cancelar perdedores. Los errores por abort evitan retries, lo que separa cancelación intencional de fallo real.
Checklist
Nombra cada fuente: usuario, timeout, admin, cuota, request padre.
Haz que cada step caro acepte signal y lo use en APIs compatibles.
Distingue run.cancel() de AbortSignal.
Guarda estados cancelled_by_user, timed_out o quota_exceeded.
Prueba limpieza de uploads, jobs externos, correos y webhooks.
Riesgos
Workflow SDK 5 sigue siendo beta/pre-release; úsalo primero en flujos internos y con rollback.
Una señal no deshace efectos remotos ni detiene código que la ignora.
Qué hacer ahora
Dibuja las fronteras de cancelación antes de añadir el botón: costo, side effects y acciones no idempotentes.
Revisión de 30 minutos
✓ Los motivos de cancelación tienen nombre de producto
✓ Cada paso costoso recibe o revisa una señal
✓ Abort y retry no se contradicen
✓ Los efectos externos tienen idempotency keys
✓ La observabilidad separa cancelled de failed
const controller = new AbortController();
const result = await Promise.race([
expensiveStep(controller.signal),
sleep("30s").then(() => null),
]);
if (result === null) controller.abort();
Fuentes y lecturas
- Vercel Changelog: Workflow SDK now supports inflight cancellation
- Workflow SDK v5 docs: Cancellation
- MDN: AbortController
- MDN: AbortSignal.any()
- Vercel Changelog: Vercel Sandbox can now run for up to 24 hours
- Reddit r/vercel: Is Workflow Development Kit production ready?
- Reddit r/vercel: Workflow devkit cleanup/cancel discussion
- Reddit r/vercel: 30 minute Functions and 24 hour Sandbox