Introduction

When Nginx experiences traffic volumes exceeding its configured connection capacity, the error log fills with "worker_connections are not enough" messages. This typically occurs during DDoS attacks, flash crowd events, or viral traffic spikes. The exact error reads:

bash
2026/04/08 15:42:33 [alert] 2345#0: 1024 worker_connections are not enough

Nginx silently drops excess connections, resulting in failed requests for users.

Symptoms

  • Nginx error log shows "worker_connections are not enough" alert messages
  • Clients receive connection refused or connection reset errors
  • ss -s shows a high number of established connections approaching system limits
  • Nginx accepts connections but fails to serve them, causing HTTP 502 or connection resets
  • Server load averages spike while response throughput drops

Common Causes

  • Default worker_connections 1024 is insufficient for high-traffic scenarios
  • OS file descriptor limit (nofile) caps the number of connections Nginx can handle
  • Each connection consumes a file descriptor, and worker_connections must not exceed the OS limit
  • Connection backlog queue overflows when all workers are saturated
  • Insufficient worker processes for available CPU cores

Step-by-Step Fix

  1. 1.Increase worker_connections and worker_processes in /etc/nginx/nginx.conf:
  2. 2.```nginx
  3. 3.events {
  4. 4.worker_connections 4096;
  5. 5.multi_accept on;
  6. 6.use epoll;
  7. 7.}

worker_processes auto; `` With worker_processes auto and worker_connections 4096`, Nginx can handle approximately 4096 x CPU cores simultaneous connections.

  1. 1.Raise the OS file descriptor limit. Edit /etc/security/limits.conf:
  2. 2.`
  3. 3.nginx soft nofile 65535
  4. 4.nginx hard nofile 65535
  5. 5.www-data soft nofile 65535
  6. 6.www-data hard nofile 65535
  7. 7.`
  8. 8.Replace www-data with your Nginx worker user.
  9. 9.Set the system-wide file descriptor limit in /etc/sysctl.conf:
  10. 10.`
  11. 11.fs.file-max = 2097152
  12. 12.fs.nr_open = 1048576
  13. 13.net.core.somaxconn = 65535
  14. 14.net.ipv4.tcp_max_syn_backlog = 65535
  15. 15.`
  16. 16.Apply with sudo sysctl -p.
  17. 17.Configure the systemd service override for Nginx. Create /etc/systemd/system/nginx.service.d/limits.conf:
  18. 18.```ini
  19. 19.[Service]
  20. 20.LimitNOFILE=65535
  21. 21.`
  22. 22.Then reload systemd: sudo systemctl daemon-reload.
  23. 23.Enable connection rate limiting to mitigate DDoS impact:
  24. 24.```nginx
  25. 25.http {
  26. 26.limit_conn_zone $binary_remote_addr zone=addr:10m;
  27. 27.limit_req_zone $binary_remote_addr zone=req:10m rate=10r/s;

server { limit_conn addr 100; limit_req zone=req burst=20 nodelay; } } ```

  1. 1.Reload Nginx and verify:
  2. 2.```bash
  3. 3.sudo systemctl reload nginx
  4. 4.sudo nginx -T | grep worker_connections
  5. 5.cat /proc/$(cat /var/run/nginx.pid)/limits | grep "open files"
  6. 6.`

Prevention

  • Monitor active connections using the Nginx stub_status module at /nginx_status
  • Set up alerts when connections exceed 70% of worker_connections capacity
  • Deploy a CDN (Cloudflare, AWS CloudFront) to absorb DDoS traffic before it reaches Nginx
  • Configure fail2ban or Nginx geo-blocking for known malicious IP ranges
  • Keep sysctl tuning documented and version-controlled for quick disaster recovery
  • Use ulimit -n 65535 in any custom startup scripts to ensure limits are applied