
📅 Publicado el 24 de octubre, 2026 · Por Equipo RedServicio
Entre todas las defensas que puedes montar frente a los abusos típicos de una API REST (fuerza bruta, scraping masivo, bots o simplemente clientes mal configurados que no paran de lanzar peticiones), el rate limiting Nginx es probablemente la que mejor relación ofrece entre eficacia y coste. Cero euros, por cierto. Aquí veremos qué es exactamente, cómo funciona el módulo nativo de Nginx que lo hace posible y cómo dejarlo configurado paso a paso, con ejemplos de código listos para copiar en tu servidor.
¿Qué es el rate limiting y por qué tu API REST lo necesita?
La idea es simple: restringir cuántas peticiones puede hacer un cliente a tu servidor dentro de un periodo de tiempo. Sin ese freno, cualquier script puede enviar miles de solicitudes por segundo y quedarse con la CPU, la memoria y el ancho de banda hasta que tu servicio se cae. Y no hace falta mala fe para que ocurra; a veces basta un cliente con un bucle mal escrito.
Para una API REST, los beneficios son bastante claros:
- Protección contra DDoS y fuerza bruta: limitas el daño que un atacante puede causar antes de ser bloqueado.
- Estabilidad: evitas que un solo cliente degrade la experiencia del resto de usuarios.
- Control de costes: menos carga innecesaria, menos recursos consumidos y una facturación de infraestructura más contenta.
- Fair use: un reparto más equitativo de recursos entre todos los consumidores de tu API.
Si tu API maneja autenticación, pagos o datos sensibles, esto deja de ser opcional. Es higiene básica de seguridad, nada más.
Cómo funciona el módulo limit_req de Nginx
Nginx trae de serie el módulo ngx_http_limit_req_module, que implementa el algoritmo de leaky bucket (cubo con fuga). La metáfora ayuda: cada cliente recibe un cubo virtual donde sus peticiones entran como agua. Si llegan a un ritmo moderado, el cubo las procesa a velocidad constante. Si llegan en ráfaga, se desborda, y las peticiones excedentes se rechazan o se ponen en cola.
Dos parámetros mandan aquí:
- rate: la velocidad máxima sostenida, por ejemplo 10r/s (diez peticiones por segundo).
- burst: el tamaño de la cola, es decir, cuántas peticiones en ráfaga se toleran antes de empezar a rechazar.
Para identificar a cada cliente, el módulo usa una clave, normalmente la IP mediante la variable $binary_remote_addr, que consume menos memoria que la IP en formato texto. Un detalle importante: si tu API está detrás de un proxy o balanceador, tendrás que usar la cabecera correcta (como X-Forwarded-For). Si no, limitarás a todos tus usuarios como si fueran uno solo. Lo he visto pasar, y no es divertido depurar por qué «la API va lenta para todo el mundo».
Configuración paso a paso de rate limiting Nginx con ejemplos de código
Vamos a la práctica. La configuración tiene dos fases: definir la zona de limitación y aplicarla a las rutas que te interesen.
Paso 1: Definir la zona de limitación
En el bloque http de tu nginx.conf, añade:
- Crea la zona: limit_req_zone $binary_remote_addr zone=api_limit:10m rate=10r/s;
- Con esto tienes una zona llamada api_limit de 10 MB, espacio de sobra para unos 160.000 estados de IP.
Paso 2: Aplicar el límite en tu location
Dentro del bloque server o location que sirve tu API:
- location /api/ { limit_req zone=api_limit burst=20 nodelay; }
Con esto, cada IP puede sostener 10 peticiones por segundo, con ráfagas de hasta 20 procesadas al instante gracias a nodelay. Sin esa opción, las peticiones en ráfaga se retrasarían en lugar de procesarse de inmediato. Depende de tu caso; no hay una opción universalmente mejor.
Paso 3: Personalizar la respuesta de rechazo
Por defecto, Nginx devuelve un 503. Para una API REST encaja mejor un 429 (Too Many Requests): limit_req_status 429;
Consejo: empieza con límites generosos y ve ajustándolos según el tráfico real. Un rate limiting demasiado agresivo romperá integraciones legítimas de tus clientes, y descubrirlo por una queja suele ser tarde.
Con estos pasos ya tienes una primera capa de protección funcionando sobre tu API REST. En la siguiente parte veremos cómo combinar varias zonas, excluir IPs de confianza y monitorizar los rechazos en los logs.
Cómo personalizar límites por cliente, ruta y tipo de tráfico
Un límite único para todo el servidor se queda corto casi siempre. La cosa es que no todos los recursos valen lo mismo: un endpoint de login no debería tolerar la misma tasa que una consulta de solo lectura, y conviene segmentar el rate limiting en Nginx según la criticidad de cada ruta.
Límites diferenciados por ubicación
Puedes declarar varias zonas y repartirlas entre distintos bloques location:
- Zona pública: limit_req_zone $binary_remote_addr zone=general:10m rate=10r/s;
- Zona de autenticación: limit_req_zone $binary_remote_addr zone=login:10m rate=1r/s;
Y en la configuración:
- En location /api/login: aplica limit_req zone=login burst=3 nodelay; para frenar ataques de fuerza bruta.
- En location /api/: aplica limit_req zone=general burst=20 nodelay; para el tráfico habitual.
Identificar clientes autenticados
Si tu API usa API keys o tokens, mejor limitar por identidad que por IP. Define una variable personalizada:
- map $http_authorization $api_client { default $binary_remote_addr; ~Bearer\s(?<token>\S+) $token; }
- limit_req_zone $api_client zone=por_apikey:10m rate=50r/s;
Con esto, quien trae token recibe un límite más generoso. El tráfico anónimo, en cambio, queda restringido a lo que permita su IP.
Excluir IPs de confianza
No te bloquees a ti mismo (pasa más de lo que parece). Combinando geo con un mapa puedes dejar fuera a tus monitores o integraciones críticas:
- geo $excluded { default 0; 203.0.113.10 1; 198.51.100.0/24 1; }
- map $excluded $limit_key { 1 «»; 0 $binary_remote_addr; }
- limit_req_zone $limit_key zone=api:10m rate=10r/s;
La clave vacía hace que Nginx no contabilice esas peticiones. Quedan, efectivamente, fuera del límite.
Errores comunes al implementar rate limiting y cómo evitarlos
- Limitar por IP detrás de un proxy o balanceador. Todas las peticiones parecen venir de la misma IP y acabas bloqueando a todos tus usuarios a la vez. Solución: usa $http_x_forwarded_for o configura real_ip correctamente.
- Olvidar el parámetro burst. Sin ráfaga permitida, las aplicaciones legítimas que hacen peticiones concurrentes fallan de forma intermitente. Y ese fallo es difícil de depurar.
- Usar la memoria por defecto sin dimensionarla. Una zona demasiado pequeña provoca errores de asignación con muchos clientes simultáneos; calcula 1 MB por cada ~16.000 IPs esperadas.
- No comunicar los límites al cliente. Devuelve cabeceras estándar como RateLimit-Limit, RateLimit-Remaining y Retry-After mediante add_header, para que tus integradores puedan adaptarse en vez de adivinar.
- Aplicar límites antes de probar en staging. Simula tráfico con herramientas como ab o k6 antes de subir la configuración a producción.
Tip: monitoriza los rechazos con grep «limiting requests» /var/log/nginx/error.log y envía el resultado a tu sistema de logs. Un pico repentino de rechazos puede indicar un ataque… o simplemente un límite mal calibrado.
Conclusión: protege tu API con rate limiting en Nginx
Pocas defensas son tan eficaces y tan baratas como el rate limiting en Nginx. Frena fuerza bruta, mitiga abusos de scraping y protege los recursos del servidor sin instalar nada adicional. El trabajo fino está en otra parte: calibrar cada zona según el tipo de tráfico, identificar bien a tus clientes y vigilar los rechazos para ir ajustando umbrales.
Eso sí, no lo veas como la solución única. Es una capa. Combínala con HTTPS, autenticación robusta y validación de entrada si quieres una protección completa. Y si prefieres no complicarte con la infraestructura, en RedServicio.net nuestros planes de hosting incluyen configuración optimizada de Nginx y soporte 24/7 para implementar todo esto sin dolor de cabeza. Tu API, y tus usuarios, te lo agradecerán.
Equipo RedServicio
Artículos escritos y revisados por nuestro equipo técnico especializado en hosting e infraestructura web en España.
¿Listo para un hosting de verdad?
Servidores en España · Soporte 24/7 en español · Migración gratuita
Ver Planes desde 3,95€/mes →