summry
Back to Build Logs
build logMay 21, 2026Updated May 30, 2026

Production Trailing Slash Redirect

A small FastAPI trailing-slash redirect became visible only after the app moved behind real HTTPS and Railway's proxy.

summrybuild-logbackenddebugginginfra

Production Trailing Slash Redirect

Problem

During the first production smoke test on summry.xyz, Google sign-in worked, but submitting a YouTube URL failed with a browser mixed-content error.

The request started correctly over HTTPS:

POST https://<api-domain>/chat

But the API returned a 307 Temporary Redirect with this location:

http://<api-domain>/chat/

The browser blocked the follow-up request because the page was loaded over HTTPS and the redirect attempted to downgrade the API call to HTTP.

Context

FastAPI uses Starlette routing underneath. Starlette redirects between slash and non-slash paths by default when a matching route exists.

Summry's backend route is registered as:

router = APIRouter(prefix="/chat")

@router.post("/")
def create_chat(...):
    ...

That means the canonical route is:

/chat/

The frontend was calling:

/chat

Locally this was harmless because the redirect stayed inside local HTTP:

http://localhost:3000 -> http://localhost:8000/chat -> http://localhost:8000/chat/

Production made the issue visible because the HTTPS request passed through Railway's edge and the generated redirect location used http://.

Implementation

The frontend now calls the canonical backend path directly:

/chat/

This avoids the redirect completely instead of relying on proxy-aware redirect behavior.

Tradeoffs

This is a small, direct fix. It keeps the backend route shape and generated OpenAPI path unchanged.

The tradeoff is that the frontend has to be precise about trailing slashes. That is acceptable here because the generated API schema already exposes /chat/, and matching the backend contract is cleaner than changing global router behavior during launch stabilization.

Lessons Learned

Localhost can hide production-only redirect issues because local development does not exercise the same HTTPS, proxy, and browser mixed-content rules.

The actual bug was not "the API is down" or "CORS is broken." It was a route mismatch that only became user-visible when a redirect crossed a secure production boundary.

For production validation, network tab details matter:

  • original request URL
  • response status
  • redirect Location
  • request scheme after redirects
  • final browser security error

Next Steps

Keep an eye out for other slash mismatches between frontend calls and FastAPI routes. If these become frequent, consider standardizing route definitions or generated-client usage so frontend paths come directly from the OpenAPI contract.