HTTP 502

502 Bad Gateway: what it means and how to fix it

The proxy in front of the real application couldn't get a usable response from it — often because it couldn't even connect, not because anything timed out.

Quick answer

A 502 comes from a proxy or load balancer, the same as a 504 — but it's a different failure. Per RFC 9110 §15.6.3: "the server, while acting as a gateway or proxy, received an invalid response from an inbound server it accessed while attempting to fulfill the request." In practice, the most common real-world cause is narrower than "invalid response" — the proxy couldn't establish a connection to the backend at all, because nothing was listening there.

This is the site's problem, not yours. Reloading rarely helps for more than a moment — if the backend is down, it's down for every visitor until someone on their end fixes it.

Where exactly it breaks

Client

sends the request

→

Proxy / load balancer

tries to reach the backend

✕

Backend

not there, or its response is unusable

Unlike a 504, the proxy isn't waiting for anything here — it either can't open a connection to the backend at all (process crashed, wrong address, network policy blocking it) or gets a response back that isn't valid HTTP, and gives up immediately either way.

If you run the service

Diagnosing a 502

  1. 1

    Confirm the backend process is actually running and bound to the right port. A crashed process, one that's still starting, or one bound to the wrong interface all look identical to the proxy: nothing to connect to.

  2. 2

    Check the backend's own logs for a crash around the same timestamp. An out-of-memory kill, an unhandled exception that took the process down, or a supervisor restart loop all correlate directly with 502 spikes on the proxy side.

  3. 3

    Verify the proxy's upstream address is actually correct. A stale IP, an old container hostname, or a typo in the upstream config produces the exact same symptom as a real outage — always worth ruling out first since it's the cheapest check.

  4. 4

    Rule out a rolling-deploy gap. Same story as 504s: the proxy may still be routing to an instance that's already been terminated, or one that hasn't finished starting yet.

Example: nginx failover across multiple backends
upstream backend {
    server 10.0.1.10:3000;
    server 10.0.1.11:3000;
}

location / {
    proxy_pass http://backend;
    proxy_next_upstream error timeout;
}

proxy_next_upstream tells nginx to try the next backend in the list if one is unreachable, instead of returning a 502 the moment the first one fails — useful once you have more than one instance to fail over to.

How HeimPulse catches this

A 502 is a real HTTP status code, so an HTTP status code assertion expecting 200 (or a 2xx range) fails as soon as it comes back — the same mechanism that catches any unexpected status. The genuinely useful part for a 502 specifically: since it's almost always a hard "backend is unreachable" failure rather than a gradual slowdown, it's exactly the kind of all-or-nothing outage that scheduled external checks catch on the next check interval, independent of whatever's happening on the backend's own host — where a process supervisor might not even know the port stopped accepting connections externally.

Frequently asked questions

Is a 502 the same as a 504?

No, even though both come from a proxy talking to a backend. A 504 means the proxy reached the backend and simply waited too long for a response. A 502 usually means the proxy never got a usable response at all — often because it couldn't even connect to the backend in the first place, which is a step earlier in the chain than a timeout.

Does a 502 always mean the backend crashed?

It's the single most common cause, but not the only one. A 502 also shows up when the proxy's upstream address is simply wrong (pointing at a port nothing is listening on, or a hostname that doesn't resolve inside the proxy's own network), or when the backend returns something so malformed the proxy can't parse it as a valid HTTP response at all.

Why does this happen right after a deploy?

A very common pattern: the proxy's upstream list still includes an instance that's already been terminated as part of a rolling deploy, or a new instance that isn't accepting connections yet. Requests routed to that instance in the gap fail with a 502 until the proxy's health checks catch up and remove it from rotation.

How does HeimPulse tell this apart from a slow backend?

It doesn't need to categorize the cause — the checker records whatever status code actually came back (502, in this case) and evaluates it against your configured HTTP status code assertion the same way it would any other unexpected code. The distinction between "crashed" and "just slow" is a diagnostic step for you, not something the check itself needs to classify.

Full uptime monitoring feature → · Alert on real patterns, not single blips → · All error explainers →

Find out the moment your backend stops responding.

Free plan, no credit card, set up in a few minutes.