Cloudflare Error 520: What It Means and How to Fix It

Cloudflare error 520 means Cloudflare reached the origin server but received an empty, malformed, or otherwise unusable HTTP response. It’s Cloudflare-specific, not a standard HTTP status code. This guide covers what triggers a 520 error code, how to diagnose it in logs, and how to fix it – whether you operate the site or scrape it.

TL;DR

  • Cloudflare returns error 520 when it reaches the origin but receives no valid HTTP response
  • Scrapers often trigger 520 when a bot layer kills a suspicious connection instead of returning 403 or a challenge
  • Compare OriginResponseStatus with CacheStatus in Cloudflare logs before changing any setting – the code shown to visitors doesn’t tell you whether the origin actually failed
  • Fix persistent 520s by aligning headers, TLS fingerprints, cookies, concurrency, and IP reputation

What is Cloudflare error 520?

Cloudflare documents the 520 error code as “web server returns an unknown error,” and defines it as the origin returning an empty, unknown, or unexpected response (Cloudflare error 520 documentation). It’s issued when the exchange between Cloudflare’s edge and the origin server ends without a usable HTTP response – the connection opened, something came back, and it wasn’t valid HTTP.

The origin server is the backend that actually hosts the site. Cloudflare sits in front of it and forwards every request, which means a visitor’s browser or a scraper talks to Cloudflare first, and Cloudflare talks to the origin:

Client -> Cloudflare edge -> Origin server -> Cloudflare edge -> Client

When the origin returns something Cloudflare can’t parse as valid HTTP, Cloudflare generates the 520 page at whichever edge server handled the request. The HTTP request was left, and no usable HTTP response came back.

Treat 520 as a failure location, not a root-cause report. It tells you the exchange broke between Cloudflare and the origin. It doesn’t tell you whether the cause was a crashed process, a firewall rule, an oversized header, or a bot layer terminating a connection on purpose.

Cloudflare error 520 is Cloudflare-specific

520 isn’t a registered HTTP status code. The IANA HTTP Status Code Registry lists the whole 512–599 block as unassigned, which is why 520 looks unfamiliar next to a 404 or a 500.

You’ll only see 520 when the target sits behind Cloudflare’s proxy. A site that doesn’t use Cloudflare exposes the underlying failure directly instead: a 500, a 502, a connection reset, or a timeout.

How Cloudflare error 520 appears

For anyone scraping sites behind Cloudflare, 520 often looks stranger than it is: the page loads fine in a browser, but the same URL returns 520 from a script. The difference comes down to headers, TLS handshake, cookies, IP range, and request timing.

Many protected origins terminate suspicious automated connections without returning a clean 403 or a CAPTCHA. Cloudflare can’t reliably distinguish that from an origin crash, so it wraps the failed exchange as 520.

How to capture the Ray ID

A Ray ID is Cloudflare’s identifier for a specific request at its edge, and it’s the one value that lets you match a failure across Cloudflare’s logs and the origin’s logs. It usually appears at the bottom of the Cloudflare error page, and it’s also returned in the cf-ray response header.

Log it alongside the URL, the timestamp with timezone, the proxy IP, the request headers, and the retry result. Without it, correlating a 520 against origin-side logs is guesswork.

Cloudflare error 520 vs. other Cloudflare 5xx errors

A Cloudflare 520 error describes one specific failure mode, and the neighboring 5xx codes describe different ones. Knowing which code you actually have keeps you from fixing the wrong layer.

Error code

What happened

What it means for you

520

Cloudflare reached the origin, but the response was empty, malformed, unexpected, or invalid.

A silent bot kill, a malformed response, oversized headers, or a transient origin crash.

Cloudflare couldn't open a connection because the origin refused it.

Usually an origin outage, a firewall rule, or a blocked Cloudflare IP range – not scraper-specific.

522

Cloudflare timed out contacting the origin: no SYN+ACK within 19 seconds, or no acknowledgment within 90 seconds after the connection is established.

If a request hangs before the Cloudflare page appears, you’re closer to 522 than 520.

523

Cloudflare couldn’t reach the origin IP at the network layer.

Routing, DNS, BGP, or origin network availability – not headers.

524

Cloudflare connected, but the origin didn’t respond before the default 120-second Proxy Read Timeout.

Long-running exports, slow pages, and overloaded origin handlers.

525 / 526

TLS failed between Cloudflare and the origin, or the origin certificate was invalid.

Retrying won’t fix it until the site operator fixes the TLS setup.

The rule: if Cloudflare reached the origin and got nonsense or nothing, it’s 520. If Cloudflare couldn’t connect or didn’t get a timely acknowledgment, it’s 521, 522, or 523. If the origin accepted the connection but took too long to respond, it’s 524. If TLS fails between Cloudflare and the origin, it’s 525 or 526.

Don’t confuse these origin-relay errors with Cloudflare’s 1xxx edge blocks. Codes like 100510091015, and 1020 mean Cloudflare itself made an access-control decision at the edge, before the origin was ever involved. A standard 500 internal server error, by contrast, points at the origin application directly. For the wider picture across providers, see our guide to proxy error codes.

Why your scraper triggers Cloudflare error 520

Most scraper-side 520s come from signals the client controls: IP reputation, browser fingerprints, headers, cookies, and request volume. The confusing part is that Cloudflare reports all of them as an unknown error, because the origin closes or breaks the response before Cloudflare can classify it cleanly.

Use the causes below to narrow down whether you’re looking at a bot block, a malformed request, an overload issue, or a temporary origin failure.

Bot detection terminates your scraper connection

The most common scraper-side cause is silent bot termination. The origin’s bot layer flags the request on signals like TLS fingerprint, header order, missing client hints, suspicious cookies, or IP reputation, then closes the connection without writing a normal response. Cloudflare sees a broken response and returns 520.

The tell: real browser traffic from the same network works, but automated traffic fails.

That behavior sits in the broader world of anti-bot systems. A strict site doesn’t need to send a tidy “blocked” page – it can drop the connection, return malformed output, or let an upstream component die before response headers are complete. All of those look like origin weirdness from Cloudflare’s side.

Bad IP reputation on datacenter proxies

If requests come from a cloud VM, a noisy datacenter proxy pool, or an ASN associated with abuse, the origin may distrust the entire range. An ASN identifies the network that announces a block of IPs on the internet.

When 520s correlate with IP range rather than with specific URLs, the problem is reputation, not broken selectors. The distinction between datacenter and residential proxies matters more here than any header tweak.

TLS and HTTP fingerprints don’t match your User-Agent

A TLS fingerprint such as JA3 or JA4 summarises details from the TLS handshake, and it can contradict the browser identity a scraper claims. If Python requests and urllib3 produce a non-browser fingerprint while the User-Agent claims Chrome, a strict origin can spot the mismatch immediately. The same applies to HTTP/2 behavior that doesn’t match the claimed browser.

Browser headers don’t match a real request

A real Chrome request includes a coherent set of AcceptAccept-LanguageAccept-Encodingsec-ch-ua, and sec-ch-ua-platform headers. A Chrome User-Agent paired with missing client hints, unusual header ordering, or values no real browser would send gives the origin an easy reason to distrust the request.

Oversized cookies and headers trigger 520

Cloudflare lists request headers exceeding 128KB as a common cause of error 520, and excessive cookies are the usual reason they get that large. Scrapers create this problem easily: a long-running stateful client keeps accumulating cookies across redirects, sessions, and retries until the request is far larger than any normal browser session would produce.

High request volume can break the origin

If parallel requests exhaust application workers, memory, or database connections, Cloudflare may establish the connection and still receive no valid response, because the origin dies mid-request. These 520s arrive in bursts that line up with concurrency spikes.

Transient origin issues cause one-off 520 errors

Some 520s are just origin noise. A deploy, a worker crash, an overloaded upstream, or a temporary Cloudflare-to-origin glitch can produce one failed request and then disappear. Treat those as retryable, but don’t let them hide a pattern – a random 520 and a repeatable scraper-only 520 are different problems.

Why a site owner’s origin returns 520

If you operate the Cloudflare-protected site, the causes below are the ones worth checking, in roughly the order they’re worth checking them. They’re origin-side failures rather than request-side ones, which is what separates them from the scraper causes above.

Origin server crashes or misconfigurations

A process that dies mid-request sends nothing Cloudflare can parse. Out-of-memory kills, unhandled exceptions, worker pool exhaustion, and failed restarts after a deploy all produce the same edge-side symptom. Application-level failures, including uncaught errors and exceptions that terminate a worker before headers are written are the single most common origin cause.

Firewalls or security software blocking Cloudflare

If an origin firewall, security module, or hosting-level protection blocks Cloudflare’s IP ranges, the connection can open and then be terminated before a valid response is written. This one is easy to miss because it often follows a firewall update or a provider migration rather than a code change.

Oversized response headers

This is the mirror image of the scraper-side cookie problem. Cloudflare lists headers exceeding 128KB as a common cause of 520, usually because of excessive cookies, and long Set-Cookie chains plus custom response headers can push a response over that ceiling. Some third-party guides still quote 8KB or 32KB – those figures are out of date, so size against Cloudflare’s own documentation rather than against a blog post.

Empty or malformed origin responses

An origin can return a technically empty body, truncated headers, or a response that violates HTTP framing. Cloudflare can’t render any of those, so it substitutes 520. Cloudflare documents two variants here: responses lacking a status code or body, and an origin that fails to return proper HTTP error responses at all. Reverse proxies and application gateways sitting between Cloudflare and the application are a frequent source, because a failure there produces malformed output rather than a clean error page.

Incorrect HTTP/2 configuration at the origin

Cloudflare opens HTTP/2 connections to any origin that announces support via ALPN. If the origin accepts that connection but then doesn’t respect or support the protocol on some routes, those routes fail while the rest of the site works. The result is a 520 that looks random until you notice it’s scoped to particular endpoints.

Authenticated Origin Pull misconfiguration

Authenticated Origin Pull has Cloudflare present a client certificate to the origin, and the origin rejects anything without it. If the certificate expires, gets rotated incorrectly, or doesn’t match what the origin expects, the origin closes the connection, and Cloudflare reports 520. This one is worth checking after any certificate renewal, because nothing else on the site changes when it breaks.

When 520 hits only some requests

A 520 that affects every request usually points at something obvious. A 520 that affects only some requests is harder, and the pattern is the diagnostic. Cloudflare specifically notes that 520s are prevalent with PHP applications that crash the origin, which is the first of the four shapes below.

Scenario

What triggers it

The diagnostic tell

PHP app crashes under a traffic spike

Worker pool and memory exhausted; the process dies before sending headers

Error rate rises and falls with memory pressure

Cookies accumulate past 128 KB

Auth redirects add state cookies without clearing obsolete ones

A fresh browser session still works; a long session doesn’t

API route exposes an HTTP/2 mismatch

Origin advertises HTTP/2 via ALPN but mishandles one route

Succeeds with curl --http1.1, fails with curl --http2

Only one visitor group gets 520

A request profile is routed down a broken application path

Chrome and fresh sessions succeed; the affected profile doesn’t

One correction worth making explicitly – if 520s appear only for Safari users, or only over a VPN, that isn’t a client TLS problem. Cloudflare terminates the visitor’s TLS at its edge, so the visitor’s TLS stack never touches the origin. Compare cookies, headers, source networks, and region-specific rules instead.

Diagnosing a 520 error

The status code shown to visitors doesn’t tell you whether the origin actually failed. The logs do. Work through these four steps in order before changing any setting.

Capture the failed request

Record the full URL, the HTTP method, the timestamp with timezone, and the Ray ID. Then establish scope: is the failure site-wide, or is it confined to certain routes, sessions, regions, or client types?

Scope is what separates a crashed origin from a bot rule, and it costs nothing to determine. A 520 on every request and a 520 on one endpoint are different investigations.

Check Cloudflare logs

In Cloudflare’s Logpush http_requests dataset, compare three fields for the failing request: EdgeResponseStatusOriginResponseStatus, and CacheStatus.

An OriginResponseStatus of 0 needs context before you act on it:

  • If CacheStatus is hit or revalidated, Cloudflare served the response from cache and never contacted the origin. The 0 is expected and means nothing failed at the origin.
  • If CacheStatus is miss or expired, Cloudflare tried to reach the origin and got nothing usable. That’s a real origin failure.

There’s a third case worth knowing – in Origin Analytics, an originResponseStatus of 200 alongside an edgeResponseStatus of 520 means the origin believes it answered successfully while Cloudflare couldn’t use what it received. That combination points at malformed framing, oversized headers, or an early connection close rather than at a crash. The Top endpoints table narrows it to specific paths.

Two practical notes on tooling. Log Explorer lets you query by a specific Ray ID, which is the fastest way to pull one failure out of the volume. Error Analytics in Zone Analytics is based on a 1% traffic sample, so treat it as a shape indicator, not a count – a low-frequency 520 may not appear in it at all.

Review origin and intermediary logs

Match the timestamp and Ray ID across every layer between Cloudflare and the application: Nginx or Apache, the load balancer, the origin firewall, and the application itself.

A clean web server log doesn’t clear the stack. If the request never reached the application, the failure sits in front of it – and the intermediary logs are where that shows up.

Test the origin directly with cURL

Compare the proxied request against a direct one. The second command pins the request to the origin IP so it bypasses Cloudflare entirely:

curl -sv https://example.com/problem-path -o /dev/null
curl -sv --resolve example.com:443:203.0.113.10 \
https://example.com/problem-path -o /dev/null

If the direct request fails too, debug the origin. If it succeeds while the proxied request returns 520, the problem is on the Cloudflare-to-origin path. Working with cURL is also the fastest way to test how sending specific headers changes the response.

One caveat: if Authenticated Origin Pull is enabled, a plain direct request isn’t equivalent, because cURL doesn’t present Cloudflare’s client certificate. A refusal in that case may be the origin working exactly as configured.

How to fix or avoid Cloudflare error 520 in your scraper

Start with the lowest-effort checks, then move toward fingerprint, traffic, and proxy fixes if the 520s keep repeating.

Fix #1: Log the Ray ID and retry once

Capture the Ray ID from the Cloudflare page or the cf-ray header, then retry after 2–5 seconds. If the retry succeeds, it was probably a transient origin problem. Log it, count it, and move on.

Fix #2: Use exponential backoff with jitter

Production scrapers need retry discipline. For 520-prone requests, use exponential backoff with jitter:

wait = min(base * 2 ** attempt + random(0, 1), max_wait)

Cap retries at 3–5 attempts. Immediate retries can worsen a stressed origin and make automated patterns louder at the same time.

Fix #3: Send a complete, browser-realistic request

Send headers that match the browser identity you’re claiming. Use a current, real User-Agent, then align AcceptAccept-LanguageAccept-Encodingsec-ch-uasec-ch-ua-platform, and a plausible Referer where the request flow calls for one. If you’re using HTTP/2, keep header behavior close to what the browser actually sends.

Fix #4: Align your TLS fingerprint with your User-Agent

A Chrome User-Agent doesn’t help if the TLS handshake says Python requests. Use a TLS-fingerprint-aware client such as curl_cffi with browser impersonation, or a real Chromium-based headless browser when the target requires it. The goal is to make the network, HTTP, and browser layers tell the same story. Our browser fingerprinting guide covers why these signals carry so much weight.

Audit the size of the Cookie header across long sessions. If it grows into tens of KB, clear non-essential cookies, isolate sessions per target, and rotate sessions sooner.

Don’t reuse a single cookie jar across unrelated URLs just because the HTTP client makes it easy. Cloudflare’s limit sits at 128 KB, but treat rapid cookie growth as a warning long before it approaches that ceiling.

Fix #6: Cap concurrency and throttle per host

If 520s appear during request spikes, reduce pressure before touching fingerprints. Start with 5–10 simultaneous requests per host and add 1–3 seconds between requests on the same connection, then raise concurrency slowly while watching the 520 rate. Throttling also breaks up the repetitive timing pattern that makes automated traffic easier to classify.

Fix #7: Rotate through residential IPs when ASN reputation is the trigger

If the same scraper works from a home connection but fails from a datacenter range, the IP layer is the likely issue. Rotating proxies spread requests across different IPs, but the proxy type matters more than the rotation itself. Decodo residential proxies route traffic through an ethically sourced residential IP network, which avoids the failures tied to noisy datacenter ranges.

Fix #8: Use a managed unblocker or scraping API for the hardest targets

Some sites layer custom bot logic on top of Cloudflare specifically to break manual automation. If 520s persist after header fixes, TLS alignment, residential rotation, and throttling, stop tuning the same script.

Decodo Site Unblocker handles proxy rotation, JavaScript rendering, browser fingerprinting, cookies, headers, retries, and fallbacks through a single endpoint. If the pipeline needs structured data rather than raw HTML, Decodo Web Scraping API returns results as HTML, JSON, CSV, XHR, PNG, or Markdown while handling retry and rendering work upstream.

Fixing 520 as the site owner

Confirm where the failure happens before changing firewall, proxy, or application settings, then work through the immediate checks below. Change one layer at a time – parallel changes make it impossible to tell which one worked.

Immediate troubleshooting

  1. Allow Cloudflare traffic at the origin. Verify the current Cloudflare IP ranges are allowlisted in the origin firewall, and confirm no security module is terminating those connections. Refresh the list on a schedule rather than treating it as a one-time change, check Cloudflare's published IP ranges for more information.
  2. Stabilize the failing process. Check for out-of-memory kills, worker exhaustion, and restart loops around the failure timestamp.
  3. Correct protocol and authentication settings. Retest HTTP/2 on the affected routes, and verify the Authenticated Origin Pull certificate if it’s enabled. If the origin announces HTTP/2 via ALPN but doesn’t honor it, you can turn off HTTP/2 to Origin under Speed, then Settings, then Protocol Optimization in the Cloudflare dashboard.
  4. Reduce response-header size. Audit Set-Cookie chains and custom headers so the total stays well under 128KB.
  5. Isolate the layer with a direct request. Reproduce the failing URL with curl --resolve pinned to the origin IP. If you test by switching DNS to DNS-only, restore proxying immediately afterward.
  6. Escalate with complete evidence. Cloudflare support needs the URL, the timestamp with timezone, the Ray ID, /cdn-cgi/trace output, and two sanitized HAR files – one with Cloudflare enabled and one with it paused.

Long-term prevention

To help prevent this from happening again, a few operational improvements can make similar issues easier to catch and less likely to reach users.

  • Monitor worker exits and 5xx rates per route, with alerts tied to deployments so a regression surfaces before visitors report it
  • Treat the Cloudflare IP allowlist as maintained configuration with a review cadence, not a one-time firewall change
  • Add automated header-size checks to session and redirect flows, where cookie chains grow fastest
  • Retest HTTP/2 and Authenticated Origin Pull after upgrades, proxy changes, and certificate renewals

Bottom line

Cloudflare error 520 tells you where the exchange failed, not why. The code appears when Cloudflare reached the origin and couldn’t use what came back, which covers everything from a crashed worker to a bot layer closing a connection deliberately.

If you operate the site, compare OriginResponseStatus against CacheStatus before changing anything, align the Ray ID and timestamp across every log layer, then compare a proxied request against a direct one. If you’re scraping, classify the failure as target-wide or scraper-specific first, then fix the single signal that triggered it – headers, TLS fingerprint, cookies, concurrency, or IP reputation. For teams that would rather not chase 520-class failures every week, Decodo’s proxy and unblocking tools remove the trigger instead of patching the symptom.

Frequently asked questions

What is error 520?

Error 520 is a Cloudflare-specific status code meaning Cloudflare reached the origin server but received an empty, malformed, or otherwise unusable HTTP response. It isn’t a registered HTTP status code, so it only appears on sites behind Cloudflare’s proxy.

How do I fix error code 520?

Start by identifying whether the origin actually failed. Compare OriginResponseStatus with CacheStatus in Cloudflare’s logs, then match the Ray ID and timestamp against origin and intermediary logs. From there, the fix depends on the cause: allowlist Cloudflare’s IP ranges at the origin firewall, resolve crashes or out-of-memory kills, reduce response headers below 128 KB, or correct HTTP/2 and Authenticated Origin Pull settings.

How to fix code 520?

Reproduce the failing URL directly against the origin with curl --resolve to isolate the layer. If the direct request also fails, the problem is at the origin. If it succeeds while the proxied request returns 520, the problem sits on the Cloudflare-to-origin path – check the firewall, header size, and protocol settings there.

How do I fix a Cloudflare error?

Identify the exact code before changing anything, because the neighboring codes have different causes. 520 means Cloudflare got an unusable response, 521 means the origin refused the connection, 522 and 523 mean Cloudflare couldn’t reach it, 524 means the origin was too slow, and 525 or 526 mean TLS failed between Cloudflare and the origin. The comparison table above maps each one to the layer that needs attention.

How do I fix error code 520 Cloudflare?

If you operate the site, work through the origin causes: crashes, firewall rules blocking Cloudflare, oversized headers, malformed responses, HTTP/2 misconfiguration, and Authenticated Origin Pull certificate problems. If you’re hitting 520 while scraping a site you don’t control, the cause is usually on your side – align your headers and TLS fingerprint with the browser you’re claiming to be, trim your cookie chain, cap concurrency, and switch to residential IPs if the failure correlates with your IP range.

© 2018-2026 decodo.com (formerly smartproxy.com). All Rights Reserved