Módulo 6: Manejo de Errores
Retry Strategies Profundizadas
Descripción de la cápsula
En G1-M06-06 viste retry on fail básico. Esta cápsula profundiza las estrategias: cuándo retry simple, cuándo exponential backoff, cuándo retry con jitter, y cómo configurarlas en n8n.
Lo que vas a aprender
- ✅ 3 estrategias de retry: fijo, exponential, con jitter
- ✅ Configurar retry on fail según estrategia
- ✅ Cuándo cada una es apropiada
- ✅ Reconocer anti-patterns comunes de retry
Estrategia 1: Retry fijo
Intento 1: wait 1s
Intento 2: wait 1s
Intento 3: wait 1s
Configuración en n8n Retry On Fail:
- Max Tries: 3
- Wait Between Tries: 1000ms
Cuándo usar
- Errores transitorios cortos
- API que se recupera rápido
- Cuando tiempos predecibles
Cuándo NO
- API saturada que necesita tiempo para recuperar (backoff es mejor)
- Rate limits (debes esperar más entre cada intento)
Estrategia 2: Exponential backoff
Intento 1: wait 1s
Intento 2: wait 2s
Intento 3: wait 4s
Intento 4: wait 8s
Cada retry duplica el wait. Filosofía: si está fallando, darle más tiempo de recuperarse.
En n8n
n8n's Retry On Fail nativo no soporta exponential directamente en algunas versiones. Workarounds:
Workaround 1: Múltiples nodos con Wait creciente
[HTTP] → fail → [Wait 1s] → [HTTP retry] → fail → [Wait 2s] → [HTTP retry] → ...
Verboso pero funcional.
Workaround 2: Code node con loop manual
let retries = 0;
const maxRetries = 5;
let result;
while (retries < maxRetries) {
try {
result = await fetch(url);
if (result.ok) break;
} catch (e) {
const wait = Math.pow(2, retries) * 1000;
await new Promise(r => setTimeout(r, wait));
retries++;
}
}
Workaround 3: SplitInBatches con Set incremental
[Set: retry_count = 0, wait_time = 1000]
│
[SplitInBatches batch=1]
│
[HTTP]
│
[IF: success?]
├─ TRUE → fin
└─ FALSE → [Set: wait_time = wait_time * 2] → [Wait dynamic] → loop back
Estrategia 3: Exponential con jitter
Igual que exponential pero con randomness:
Intento 1: wait 1s ± random(0-0.5s) = 0.5-1.5s
Intento 2: wait 2s ± random(0-1s) = 1-3s
Intento 3: wait 4s ± random(0-2s) = 2-6s
Por qué jitter
Si 1000 clientes tienen retry exponential sincronizado sin jitter, todos reintentan al mismo tiempo:
- Intento 1 fallido a las 12:00:00 → todos retry a 12:00:01
- API recibe 1000 requests simultáneas → falla otra vez
- Loop interminable
Con jitter, los retries se distribuyen en una ventana → la carga es manejable.
Implementación en Code node
const baseWait = Math.pow(2, retries) * 1000;
const jitter = Math.random() * baseWait * 0.5;
const totalWait = baseWait + jitter;
Decisión: qué estrategia
| Caso | Estrategia |
|---|---|
| API muy estable, errores raros | Retry fijo simple |
| API que se sobrecarga | Exponential backoff |
| Múltiples clientes/instances | Exponential con jitter |
| Rate limits del API | Wait Retry-After específico (no retry pattern) |
Max retries: ¿cuántos?
Demasiado pocos (1-2)
Errores transitorios de medio plazo no se recuperan en 2 retries.
Demasiado muchos (10+)
- Workflow tarda mucho en fallar definitivamente
- Si el error es no-transitorio, son retries inútiles
- Consume recursos sin beneficio
Rango razonable
3-5 retries cubre la mayoría de transients sin desperdiciar recursos.
Para casos especiales:
- APIs muy críticas con SLA estricto: 5-7
- Operaciones idempotentes seguras: hasta 10
- Operaciones que tienen costo monetario por intento: 1-2
Retry con condición
A veces quieres retry solo si la condición lo amerita, no en todos los errores.
Patrón
[HTTP con Continue on Fail]
│
[IF: error es transient?]
├─ TRUE → [Wait + retry HTTP] (loop hasta max)
└─ FALSE → [skip + log] o [alert]
Categoriza el error (cápsula 02) antes de decidir retry.
Anti-patrones del retry
Anti-pattern 1: Retry sin max
Loop infinito. Workflow nunca termina.
Fix: siempre max retries.
Anti-pattern 2: Wait muy corto en exponential
Intento 1: wait 100ms
Intento 2: wait 200ms
Intento 3: wait 400ms
Demasiado rápido. La API no tiene tiempo de recuperarse.
Fix: empezar con 1s mínimo.
Anti-pattern 3: Retry para errores 4xx
400/404 no se arreglan con retry. Es bug.
Fix: clasificar antes de retry.
Anti-pattern 4: Retry sin logging
Workflow reintenta 5 veces sin loggear. Después falla. No sabes por qué.
Fix: log cada intento con razón del fallo.
Anti-pattern 5: Retry crítico sin alert
Workflow falla todos los días por 30 días. Nadie revisa. Cliente pregunta por qué no funciona.
Fix: alert cuando max retries se alcanza.
Cap en exponential
Sin cap, después de 10 retries esperas 1024 segundos (~17 min).
Implementación
const wait = Math.min(Math.pow(2, retries) * 1000, 60000); // cap 60s
Ejemplo: workflow con retry inteligente
[Trigger]
│
[HTTP con Continue on Fail]
│
[Set: clasificar error]
│
[Switch: error_category]
├─→ "success" → continuar
├─→ "transient" → [Retry hasta 3, exponential] → continuar o alert si falla
├─→ "rate_limit" → [Wait Retry-After + retry 1] → continuar o alert
├─→ "auth" → [Alert inmediato] → terminar
└─→ "client_error" → [Log + skip] → continuar
Cada categoría su estrategia.
Resumen
- 3 estrategias: fijo, exponential, exponential con jitter
- Jitter importante en sistemas distribuidos
- Max retries 3-5 razonable para mayoría
- Cap el wait para no esperas excesivas
- Categorizar antes de retry
- 5 anti-patterns: sin max, wait muy corto, retry para 4xx, sin logging, sin alert
Lo que sigue: Continue on Fail patterns — manejar fallos sin parar el flow.
Creado: Mayo 11, 2026 Versión: 1.0