Toda funcionalidad que envía correo llega con límites: topes por usuario para frenar el spam, topes por bandeja para proteger las bandejas, cuotas del proveedor para proteger la reputación. La pregunta de ingeniería nunca es si existen los límites, sino si se comportan correctamente al alcanzarse: errores limpios, cabeceras Retry-After honestas y una notificación visible para el usuario que diga qué pasó y cuándo se restablece. Probar esto contra usuarios reales es buena forma de perder usuarios reales. Las bandejas desechables nuevas hacen probable toda la superficie sin molestar a nadie.
Mapea los límites antes de probarlos
No puedes hacer aserciones sobre límites que nadie escribió. Inventario primero:
- Topes por bandeja: máximo de mensajes por bandeja por ventana.
- Topes por cuenta: correo de verificación o restablecimiento por hora y por usuario — el flujo de restablecimiento de contraseña es donde más aparece, cubierto en cómo probar correos de restablecimiento de contraseña.
- Topes por IP y por tenant: límites de toda la organización o de nivel de infraestructura.
- Cuotas del proveedor: los propios throttles de tu proveedor de envío, cuyos errores tu aplicación debe traducir, nunca filtrar.
De cada uno, registra desde configuración o código: la ventana, el tope, la acción al incumplir — encolar, rechazar con un 429, o el imperdonable descarte silencioso — y si debe dispararse un correo de notificación. Esa tabla se convierte en tu lista de aserciones.
El flujo de prueba de límites de tasa
1. Provisiona una bandeja nueva por ejecución. [Crea una bandeja temporal](/), o provisiona por API como se describe en correo temporal para cuentas de prueba QA. El estado limpio importa: los contadores heredados son la primera fuente de resultados confusos. 2. Encuentra el tope real. Léelo de la configuración. Si no es configurable, sondea hasta que cambie el comportamiento y confirma el borde con envíos exactamente-en-el-tope y tope-más-uno. 3. Dispara una ráfaga controlada. Golpea el endpoint en un bucle cerrado, registrando cada respuesta: estado, cabeceras, cuerpo. Quieres la primera respuesta limitada y la prueba de que las anteriores estaban limpias. 4. Verifica la semántica del 429. Código de estado correcto — no un 500, no un 200 seguido de nada —, un Retry-After legible por máquinas que coincida con la ventana real, un payload de error estable que los clientes puedan parsear, y sin envíos parciales: encolado o rechazado, nunca ambos. 5. Comprueba el correo de notificación. Donde el diseño diga que se avisa al usuario — cuota cercana, cuota excedida —, afirma que el correo llega a la bandeja temporal, indica el límite y la hora de restablecimiento, y coincide con la realidad. 6. Verifica la recuperación. Tras expirar la ventana, el envío debe volver a funcionar sin desatascos manuales, y una notificación de límites-levantados, si la envías, debe dispararse exactamente una vez. 7. Repite con tráfico sostenido justo por debajo del tope durante varias ventanas; la siguiente sección explica por qué.
Prototipar el bucle es más rápido en el probador de API, y un receptor como el probador de webhooks captura las llegadas de notificaciones sin retardo de polling.
Ráfaga contra sostenido: por qué debes probar ambos
Los limitadores de tasa son algoritmos, y los algoritmos tienen formas. Un limitador de ventana fija se comporta educadamente bajo un flujo sostenido pero reinicia todo su presupuesto en el borde de la ventana — dos ráfagas a caballo de un borde pueden duplicar efectivamente el tope. Un cubo de fichas absorbe ráfagas hasta el tamaño del cubo y luego limita con suavidad. Una ventana deslizante es más justa pero más cara de verificar. Prueba una sola forma de tráfico y habrás probado un modo, con los demás lanzados sin verificar. Lo mismo aplica a las notificaciones: una prueba de ráfaga muestra si el correo de excedencia se dispara una vez, mientras que una prueba sostenida revela si avisas en cada envío rechazado o una vez por ventana.
Sobre qué hacer aserciones
- Estado y cabeceras: 429 donde está documentado, Retry-After consistente con la ventana configurada, cabeceras de límite presentes si las prometes.
- Estabilidad del payload de error: el código de error sobre el que ramifican los clientes no debe derivar entre releases; fíjalo con una prueba.
- Contenido de la notificación: el valor del límite, la hora de restablecimiento y una salida están presentes, y la hora coincide con el comportamiento observado.
- Desduplicación: exactamente un correo de excedencia por ventana — no uno por petición rechazada.
- Higiene de estado: tras la recuperación un envío normal funciona, y los contadores no filtran entre usuarios ni bandejas.
- Sin descartes silenciosos: cada envío se entrega, se encierra en cola o se rechaza explícitamente, y los rechazos son visibles en los logs.
Falsos positivos frecuentes
- Contadores sucios: la prueba de ayer consumió el presupuesto de hoy, el limitador se dispara pronto, y el bug que reportas va contra ti mismo. Bandeja y cuenta nuevas por ejecución.
- Throttling del proveedor leído como throttling de la aplicación: el error de cuota del proveedor sale como tu 429. Comprueba qué capa rechazó el envío antes de reportar; los logs de envío suelen resolverlo de un vistazo.
- Desviación de reloj en los bordes: si la máquina de prueba y el limitador discrepan en la hora, las pruebas de borde parpadean. Conduce las aserciones desde las marcas de tiempo del servidor en las respuestas cuando sea posible.
- Suites paralelas compartiendo un tope de tenant: dos pipelines ejecutándose a la vez se reparten un presupuesto y ambos observan throttling antes de lo esperado.
Preguntas frecuentes
¿Cómo pruebo los límites de tasa sin un proveedor real en el bucle? Apunta staging a un sumidero o un proveedor mock para la lógica pura del limitador, pero mantén al menos una ruta por la canalización real — los correos de notificación en sí necesitan entrega genuina para verificarse, que es donde las bandejas desechables se ganan el puesto.
¿Debe el correo de cuota excedida ir a la bandeja que está sobre la cuota? Normalmente, si esa bandeja todavía puede recibir. Si el tope está aguas arriba, envíalo a la dirección principal de la cuenta. Lo que nunca debe pasar es que la notificación quede bloqueada en silencio por el propio limitador del que informa — exime las notificaciones del sistema de los topes de usuario y prueba esa exención explícitamente.
¿Cuál es la aserción que más se pasa por alto? La recuperación. Los equipos machacan el throttle y nunca verifican que el envío vuelva a funcionar tras la ventana, o que los contadores se reinicien por bandeja y no globalmente.
¿Cuántos envíos necesita cada prueba? Los suficientes para cruzar el borde por ambos lados: exactamente en el tope, tope más uno, y una ráfaga muy por encima. Si el tope es grande, hazlo configurable en entornos de prueba en vez de enviar miles de mensajes reales.
En resumen
La limitación de tasa es una funcionalidad con interfaz de usuario, y buena parte de esa interfaz es email: avisos de cuota, notificaciones de excedencia, confirmaciones de restablecimiento. Prueba los límites como cualquier otro contrato — ráfaga y sostenido, exactos en el borde, con aserciones sobre códigos de estado, cabeceras, estabilidad del payload y el contenido y el momento de los correos de notificación. Bandejas desechables nuevas por ejecución mantienen limpio el estado de los contadores, para que midas el limitador y no las sobras.
