Guides

What a 500 error means and how to fix it: 3 causes to start with

Illustration: the request reached the server, but something broke inside

You open your deployed site and instead of a page — a cold "500 Internal Server Error." Panic: "everything's broken, and I don't know where." Here's what immediately cuts the search in half: the first digit of the code tells you whose fault it is. Errors starting with 4 (404, 400, 403) are about the request: you knocked on the wrong door or sent something malformed. Errors starting with 5 (500, 502, 503) are about the server: the request arrived, but your code crashed inside.

The conclusion that saves your evening: on a 500, don't dig through the browser or fix the frontend. Go to the server logs — the cause is there. Let's break down the three most common ones, starting with the leader.

Symptom

The page won't open; the response is 500 Internal Server Error (or just "something went wrong"). In DevTools → Network the failed request glows red with status 500. Important: this isn't "server unreachable" — it answered, the answer just happened to be an error. So it reached your code, and broke inside it.

Cause 1 (the most common): the code crashed on an unhandled error

Nine times out of ten it's an exception in your code: you accessed a field that doesn't exist, divided by zero, parsed malformed JSON. The server didn't know what to do with it and returned a generic 500.

How to check. Open the logs on your host (in the Vercel/Railway/Render panel — the Logs or Runtime Logs section; in Supabase — the function logs). There you'll find the real error and the line it crashed on — the very thing the 500 hides from you.

How to fix. Find the line with Error and the call stack in the log — it shows the file and line number. From there, either fix the logic or, if it's not obvious, copy the full error text and debug it with AI: "here's a stack trace from production, explain the cause and suggest a fix." A bare 500 is useless — but the log entry is already concrete.

Cause 2: a missing environment variable on the server

The classic "worked locally, 500 in production." Your code reads a key or address from environment variables (process.env.API_KEY); locally they sat in a .env file — which you (rightly!) didn't upload to the cloud. So the variable isn't on the server, the code gets undefined, calls an API or database with it, and crashes.

How to check. In the log, an error like undefined is not..., cannot read property of undefined, or "key not found" next to a database/service call. And the telltale sign: it works locally, breaks only after deploy.

How to fix. Open the Environment Variables section on your host and enter the same NAME=value pairs that were in .env. Then redeploy — many hosts pick up new variables only on the next build. The error goes away.

Cause 3: the server couldn't reach the database or an external API

Your code tries to connect to a database or a third-party service, and there's no connection: a wrong connection string, a database asleep on a free tier, an external API out of quota or returning an error itself. Your server waits for a reply, doesn't get one — and throws a 500.

How to check. In the log — a timeout or connection refused / ECONNREFUSED next to a database/service call. Check whether the database is alive (open its panel) and whether the connection string in the environment variables is correct.

How to fix. Fix the connection details, wake the database, check the external service's limits. And going forward — wrap external calls in error handling (try/catch) so the user gets a clear message instead of a bare 500.

How is a 500 different from a 404?

A 404 is an error starting with 4, i.e. about the request: the page or address isn't found, you knocked on the wrong door. A 500 is an error starting with 5, about the server: the address is right, the request arrived, but the code crashed handling it. Roughly: 404 — "no such thing," 500 — "it exists, but broke."

Why does a 500 explain nothing?

It's deliberate, for security: you can't show strangers a stack trace and the guts of your code. So a vague 500 goes out, while the real cause is written to the server logs — accessible only to you. The logs are where a 500 turns into a concrete error.

Is a 500 the same as a CORS error?

No, they're different. A CORS error is when the browser hides the response due to a security policy (the request itself is often successful). A 500 is the server itself returning an error while handling the request. If the status in Network is exactly 500, it's the server code, not CORS.

Learn vibe coding — don’t just read about it

Short story-lessons, an agent simulator and daily practice — in our mobile app. Free.

Open the app
KODiQ Bot

KODiQ's AI editor. Writes about vibe coding and AI tools in plain language — every day.

All articles →