DeployReactRouting

Page works until I refresh, then 404 (React Router / SPA on static hosting)

404: NOT_FOUND when refreshing /dashboard or opening a direct link

In short: Your single-page app handles routes in the browser, but the host looks for a real file at /dashboard and doesn't find one.

Why it happens

Client-side routers (React Router, etc.) only work after index.html loads. On a hard refresh, the static host gets a request for /dashboard, has no such file, and returns 404 unless told to fall back to index.html.

How to fix it

  1. Vercel: add a rewrite in vercel.json sending all paths to /index.html.
  2. Netlify: add public/_redirects containing /* /index.html 200.
  3. Cloudflare Pages: if there's no top-level 404.html, Pages serves the app as an SPA automatically. Remove a stray 404.html if routes 404.
  4. GitHub Pages: no rewrites. Use hash routing or a 404.html that redirects.
  5. Make sure real API routes or static files aren't swallowed by the catch-all.

Example

// vercel.json
{
  "rewrites": [{ "source": "/(.*)", "destination": "/index.html" }]
}
Don't: Don't switch the whole app to server rendering just for this.

Copy-paste fix prompt

Paste into Cursor, Claude Code, Codex, Lovable, Bolt, Replit or v0
I'm getting this error in my app:

404: NOT_FOUND when refreshing /dashboard or opening a direct link

[Paste the full error, stack trace, and the file it points to here]

Likely cause: Your single-page app handles routes in the browser, but the host looks for a real file at /dashboard and doesn't find one.

Task: Identify my host and router, then add the exact SPA fallback config file for that host without breaking API routes or static assets.

Rules:
- First explain the root cause in 2 sentences and list the files you'll change.
- Make the smallest change that fixes it. Don't refactor unrelated code.
- Don't disable security or checks (RLS, auth, signature verification, type checking, CORS allow-all) to make the error disappear.
- Never print or hard-code secret keys.
- Finish by telling me exactly how to verify the fix.

Common with: Lovable, Bolt, Cursor. Last reviewed 2026-11-13.

Related fixes

← All fixes · Still stuck? Use the diagnose-first prompt