HTTP Status Codes Error 502: Bad Gateway
A proxy or load balancer got an invalid or no response from the upstream app (refused, reset, crashed). Check that the upstream is running on the expected host:port and that its keep-alive timeout exceeds the proxy's.
Identify: does your log match?
HTTP/1.1 502 Bad Gateway Server: nginx/1.27.2 2026/10/22 13:07:44 [error] 31#31: *1842 connect() failed (111: Connection refused) while connecting to upstream, client: 172.18.0.1, server: api.example.com, request: "GET /v1/orders HTTP/1.1", upstream: "http://172.18.0.5:3000/v1/orders", host: "api.example.com"
- High
Upstream app down or wrong port
The app crashed, is restarting, or listens on a different port than proxy_pass/target group points to.
- High
Keep-alive timeout race
Node.js closes idle sockets after 5s by default while an ALB keeps them 60s. The LB reuses a socket the app just closed and gets a reset.
- Low
Response headers too large
Big cookies or headers exceed proxy_buffer_size, so nginx rejects the upstream response as invalid.
Fix
Set keepAliveTimeout above the load balancer idle timeout
const server = app.listen(3000); // keepAliveTimeout defaults to 5s
const server = app.listen(3000, '0.0.0.0'); // ALB idle timeout is 60s: keep sockets open longer than that server.keepAliveTimeout = 65_000; server.headersTimeout = 66_000;
The upstream must never close an idle connection before the load balancer does, or in-flight reuse produces 502s.
Verify: reproduce it on purpose
$ docker run --rm -d -p 8080:80 --name p nginx:alpine sh -c "echo 'server{listen 80;location /{proxy_pass http://127.0.0.1:9;}}' > /etc/nginx/conf.d/default.conf && nginx -g 'daemon off;'" && sleep 1 && curl -i localhost:8080; docker rm -f pRun it against a dev environment to trigger 502 on purpose and test your error handler.
Prevent
- Add a /healthz endpoint and an LB health check.
- Graceful shutdown: stop accepting, drain, then exit.
- Alert on upstream 5xx separately from app 5xx.
FAQ
What is the difference between 502 and 504?
502 means the upstream answered badly or refused. 504 means it did not answer before the proxy timeout.
Why do 502s spike during deploys?
Old instances are killed while the LB still routes to them. Use readiness checks and connection draining.
Is 502 safe to retry?
For idempotent requests, yes, once with backoff. For POSTs, use an idempotency key first.
Related errors
Last verified 2026-10-22 · Source: IANA HTTP Status Code Registry (RFC 9110) · Official docs ↗ · ~60,500 searches/mo