503 Service Unavailable
The body decides it. An outage page is the site, a challenge page is the site blocking you, and a tunnel error is the proxy path.
- Usually from
- Usually the target; sometimes the proxy path
- Try first
- Read the body: outage page, challenge page, or tunnel error
What a 503 means through a proxy
The straightforward 503 means down for maintenance, or overloaded and asking you to come back later. Those hit every visitor, with or without a proxy.
Some bot-protection services answer suspect traffic with a 503 and a challenge page where others would use 403. Same status, different meaning: that one is a block.
A proxy can send 503 on the CONNECT when it has no way to serve you at that moment. For an HTTPS target your tool reports that as a tunnel error, separate from any response.
Your credentials, the proxy, or the target?
The body decides it. An outage page is the site, a challenge page is the site blocking you, and a tunnel error is the proxy path.
Your credentials
Not the cause. Credentials fail with a 407.
The proxy
When the 503 arrives as the answer to CONNECT. Check the status bot, then retry.
The target site
When it arrives as a response. Either the site is struggling, or it is pushing back on your traffic.
How to tell
- A 503 that also happens without the proxy is a site outage.
- A 503 only through the proxy, with a challenge or "checking your browser" page, is bot protection. Treat it as a 403.
- A
Retry-Afterheader on a 503 usually means real maintenance or overload. - In curl, a
%{http_connect}of 503 means the proxy sent it during CONNECT.
Fixes, in the order to try them
- Costs nothing
Check the site without the proxy
If it is down for everyone, wait, and honour Retry-After if the response has one.
- Costs nothing
Check the status bot
For a 503 on the CONNECT, incidents on our side are posted by the status bot in Discord. If it is quiet, post the curl output in the Discord.
- Costs nothing
Retry later, with backoff
A real 503 is temporary. Back off exponentially, cap the attempts, and move on to other URLs in the meantime.
- Costs some time
Treat a challenge page as a block
Slow down, send normal headers, keep cookies with one address and respect
robots.txt. The 403 page has the full list. We do not help with solving challenges. - Costs money
Move off datacenter if only hosting ranges get the challenge
If the challenge appears on datacenter IPs and not from a home connection, residential or ISP addresses fix it, the same as with a 403.
See the real status and headers
Each sample saves the headers and the body, so you can see which of the three kinds of 503 you have.
curl
curl -s -o page.html -D headers.txt -x http://USER:[email protected]:8000 \
-w 'CONNECT %{http_connect} / site %{http_code}\n' https://example.com/
grep -iE '^(retry-after|server)' headers.txt
grep -ioE 'maintenance|checking your browser|captcha' page.html | sort -uPython Requests
import requests
URL = "https://example.com/"
PROXY = "http://USER:[email protected]:8000"
via_proxy = requests.get(URL, proxies={"http": PROXY, "https": PROXY}, timeout=30)
direct = requests.get(URL, timeout=30)
print("proxy:", via_proxy.status_code, "direct:", direct.status_code)
if via_proxy.status_code == 503:
print("retry-after:", via_proxy.headers.get("Retry-After"))
print("server:", via_proxy.headers.get("Server"))
print(via_proxy.text[:300])Scrapy
# settings.py
RETRY_HTTP_CODES = [500, 502, 503, 504]
RETRY_TIMES = 2
# in the spider
handle_httpstatus_list = [503]
def parse(self, response):
if response.status == 503:
self.logger.warning(
"503 at %s, retry-after=%s", response.url, response.headers.get("Retry-After")
)
returnPlaywright
from playwright.sync_api import Error, sync_playwright
PROXY = {"server": "http://resi.proxymonkey.io:8000", "username": "USER", "password": "PASS"}
with sync_playwright() as p:
browser = p.chromium.launch(proxy=PROXY)
page = browser.new_page()
response = page.goto("https://example.com/")
if response.status == 503:
print(response.headers.get("retry-after"), "|", page.title())
page.screenshot(path="503.png")
browser.close()The page title alone usually tells a maintenance page from a challenge page.
Node.js
import { fetch, ProxyAgent } from "undici";
const dispatcher = new ProxyAgent("http://USER:[email protected]:8000");
const res = await fetch("https://example.com/", { dispatcher });
if (res.status === 503) {
console.log("retry-after:", res.headers.get("retry-after"));
console.log("server:", res.headers.get("server"));
console.log((await res.text()).slice(0, 300));
}The samples use the residential gateway, resi.proxymonkey.io:8000. For an ISP or datacenter IP, use USER:PASS@IP:PORT for the address you rented. Your dashboard lists the host and port for every order, and where it differs from this page, the dashboard is right.
Will a different proxy line fix it?
When switching helps
A challenge-page 503 that only appears on datacenter IPs. Residential and ISP addresses get the treatment a home connection gets.
When it will not
An outage or a maintenance 503 hits every visitor. No proxy line routes around a site that is down.
Is a failed request billed?
We bill for request bytes and response bytes, including headers and protocol overhead on the tunnelled connection. Connections that fail before transferring data are not billed. Retries that you initiate are billed and appear as separate entries in your usage log.
A 503 that came back from the site is a response like any other, and the terms bill request and response bytes. For a 503 from the proxy on the CONNECT, the terms say connections that fail before transferring data are not billed, without saying where a proxy error sits against that line. If you see rows for them, ask in Discord.
Residential is billed per GB of that traffic. ISP and datacenter addresses are charged per IP for their term, and where a plan includes a traffic allowance, traffic past it is billed per GB under the same rule. The usage log in your dashboard has one row per request with bytes in, bytes out and cost, so you can look up the failed request yourself.
Questions people ask about a 503
Why do I get 503 through the proxy but not in my browser?
That pattern points at bot protection. Your browser has cookies, a normal set of headers and a history with the site; a fresh script has none of those, and the site answers with a challenge. Treat it as a block: slow down, send normal headers, and if the site still refuses, look for an official API.
Is a 503 temporary?
It is supposed to be. Maintenance and overload 503s clear on their own, often within the time Retry-After gives. A 503 that never clears for you while the site works for other people is a block.
How do I know if the proxy itself is down?
Check the status bot in Discord. Then run one curl command that prints %{http_connect}. A 503 there is the proxy. A 200 there means the tunnel opened and the proxy did its part.
Does a 503 mean my IP is banned?
Not on its own. A ban usually looks like a steady 403, or a challenge on every request. A 503 with Retry-After is a site asking everyone to come back later.
Errors that travel with this one
- 502
502 Bad Gateway
A go-between got a bad answer from the next hop. Could be the proxy, could be the site’s own load balancer.
Work it out → - 429
429 Too Many Requests
The site says you are going too fast, and it often says for how long.
Work it out → - 403
403 Forbidden
The website refused you. Through a proxy that is usually about the IP range, your headers or your pace.
Work it out →
Still stuck on a 503?
Paste your error in the Discord: the full message plus the command or the few lines that set up the proxy, with the password taken out. Someone there has seen it before.
Join the Discord4,200+monkeys in the Discord
Help from humans
Post your error, get an answer. Usually in minutes, usually from someone who has hit the same wall.
A status bot that tells on us
Pool health, incidents and maintenance posted automatically. Including the bad days.
Deals and free traffic
Bonus GB drops, early access to new pools, and the occasional giveaway for a good bug report.