DEV Community

Cover image for The nginx proxy_pass Trailing Slash Detail That Caught Me
Schiff Heimlich
Schiff Heimlich

Posted on

The nginx proxy_pass Trailing Slash Detail That Caught Me

Here's something that'll make you waste an afternoon if you're not careful.

You're setting up nginx as a reverse proxy. You have a location block, and inside it you use proxy_pass to forward to your backend. Simple enough.

But there's this one detail about trailing slashes that changes everything, and it's not obvious until you've been burned by it.

The Two Behaviors

With a trailing slash:

location /api/ {
    proxy_pass http://backend/;
}
Enter fullscreen mode Exit fullscreen mode

A request to /api/users becomes /users at the backend. The /api/ prefix gets stripped.

Without a trailing slash:

location /api/ {
    proxy_pass http://backend;
}
Enter fullscreen mode Exit fullscreen mode

A request to /api/users stays /api/users at the backend. The full path is preserved.

That's it. One slash changes whether your backend sees /users or /api/users.

A Simple Mental Model

Think of it this way:

  • Slash present = "replace the matched location with this"
  • No slash = "prepend this to the existing path"

With the slash, nginx treats it as "strip the prefix and replace with what's after the slash." Without it, it just passes through unchanged.

When This Matters

Most of the time you want the slash-stripping behavior. Your backend doesn't need to know it's mounted at /api/ — it just wants /users.

But sometimes your backend expects the full path. Maybe it's serving multiple apps and uses the prefix to route internally. Then you leave the slash off.

When to Use rewrite Instead

If you need something more complex — like renaming paths or doing conditional routing — don't try to hack it with proxy_pass slashes. Just use rewrite:

location /api/ {
    rewrite ^/api/(.*)$ /v2/$1 break;
    proxy_pass http://backend;
}
Enter fullscreen mode Exit fullscreen mode

Now /api/users becomes /v2/users at the backend. Clear, explicit, no magic.

The Takeaway

When you're setting up a reverse proxy:

  1. Check if your backend expects the prefix or not
  2. Add or remove the trailing slash accordingly
  3. If you need anything fancier, use rewrite instead of trying to be clever

It's one character. But it'll cost you two hours of debugging if you get it wrong.

Top comments (1)

Collapse
 
kashif_manzer profile image
Kashif Manzer •

One related gotcha that catches people: the trailing slash replacement silently stops working when the proxy_pass target contains variables, like when you resolve the backend through a resolver. In that case nginx passes the request URI as received and the slash rule no longer applies, so you have to rewrite the path explicitly instead. Good write-up, this really is a one character change that can cost hours.