corsproxy.io not working? 401, 403, and what changed
If corsproxy.io/?url=... calls that used to work now fail, the most likely cause is a policy change, not an outage. corsproxy.io now requires an API key on every request, and its free keys are meant for development origins only. This post shows how to tell which error you have and what to do about each.
Disclosure: corsproxy.dev is a different company and a competing product. Everything about corsproxy.io below comes from their FAQ and 403 guide, plus our own requests on the date above. Check their docs for current terms.
Check which error you have
Your browser console will usually say "blocked by CORS policy" whatever went wrong, because an error response from the proxy may not carry the header the browser is looking for. Ask the proxy directly instead:
curl -s -w '\n%{http_code}\n' "https://corsproxy.io/?url=https://example.com"
Without a key, that currently returns 401 with this body:
{"error":"A valid API key is required. Get one at https://console.corsproxy.io/"}
401: no key, or the key isn't valid
corsproxy.io's FAQ now says every proxy URL needs an API key, and that you can't use the service without creating an account. Keyless calls that worked in older tutorials, gists and Stack Overflow answers stopped working because of this. The FAQ also says free accounts created before 8 November 2026 keep their existing access, so a teammate's older key may keep working while a new one behaves differently.
The fix on their side is to create an account and add key=YOUR_KEY to the URL.
403: plan limits, or the target is blocking
Their 403 guide lists two groups of causes:
- The proxy refused it. A missing or invalid key for a feature that needs one, parameters reserved for higher plans (
extract,input,output,ttl), or a private or local network target such as127.0.0.1. - The target site refused it. Many sites block datacenter IPs, bots or certain user agents. Some finance APIs and RSS feeds are named as examples.
To tell them apart, request the target URL directly from your own machine with curl. If that also returns 403, no proxy will fix it, including ours: the upstream is blocking automated traffic, and you need its official API or a server you run yourself.
It works on localhost but not on your live site
Per their FAQ, a free key works from localhost and other development origins, with 10,000 requests and 1 GB a month. Production domains need a paid plan. So a free key that works in development can fail once the same code is deployed. That's expected under their current terms, not a bug.
Your options
- Stay and add a key. If you're only developing locally, a free corsproxy.io key covers it. For a live site, their paid plans start at $5 a month; see our side-by-side comparison for what each includes.
- Check you need a proxy at all. If the request runs on a server, in a build step or a cron job, CORS doesn't apply. Call the upstream directly. When not to use a CORS proxy covers the other cases.
- Self-host. We publish an MIT-licensed Go relay you can run yourself. You own uptime and abuse handling.
- Switch to corsproxy.dev. A free key works on any origin, including your live site: 500 requests and 250 MB a day, no card. Pro is $5 a month for 20,000 requests and 10 GB a day.
The switch, if you pick us
Both services take an encoded target URL and a key, so it's a one-line change:
const target = encodeURIComponent('https://api.example.com/data');
// corsproxy.io
fetch(`https://corsproxy.io/?key=YOUR_CORSPROXY_IO_KEY&url=${target}`);
// corsproxy.dev
fetch(`https://api.corsproxy.dev/proxy?url=${target}&key=YOUR_CORSPROXY_DEV_KEY`);
The reqHeaders, resHeaders and ttl parameters work the same way here (ttl needs Pro). We accept GET and POST only, and we don't do file conversion or image transforms. If you rely on those, stay with corsproxy.io.
Lock your key to your site's origin in the dashboard. That stops other websites from reusing it in a browser, though not a script that forges the Origin header.
Moving off corsproxy.io
Get a free key, change the host, and your fetch calls work again, on localhost and in production.