# URIs, Timeouts, Buffering and WebSockets — Nginx

Source: https://www.skillbyai.com/en/nginx/p-details

> Get proxy_pass URI rewriting, timeouts and WebSocket upgrades right.

## The details that cause outages

**URI handling**: if `proxy_pass` has **no URI part** (`proxy_pass http://app;`), the original request URI is passed unchanged. If it **has a URI part**, even just a slash (`proxy_pass http://app/;`), the part of the request URI matching the **location prefix is replaced** by it: with `location /api/ { proxy_pass http://app/; }`, `/api/orders` becomes `/orders` upstream. **Timeouts**: `proxy_connect_timeout` (establishing the connection, default 60 s, usually far too long), `proxy_read_timeout` (between two successive reads of the response, default 60 s) and `proxy_send_timeout`. **Buffering**: by default NGINX buffers upstream responses, freeing the application quickly even for slow clients; disable it with `proxy_buffering off;` for streaming responses such as Server-Sent Events. **WebSockets** need HTTP/1.1 and the `Upgrade` and `Connection` headers passed explicitly, plus a long `proxy_read_timeout`, because hop-by-hop headers are not forwarded by default.

## API prefix stripping, SSE and WebSockets

Each location shows one of the common special cases.

```nginx
map $http_upgrade $connection_upgrade {
    default upgrade;
    ''      close;
}

server {
    listen 80;
    server_name app.example.com;

    location /api/ {
        proxy_pass http://api_backend/;         # /api/orders -> /orders upstream
        proxy_connect_timeout 2s;
        proxy_read_timeout 15s;
    }

    location /events/ {
        proxy_pass http://api_backend;          # URI passed unchanged
        proxy_buffering off;                    # stream Server-Sent Events immediately
        proxy_read_timeout 1h;
    }

    location /ws/ {
        proxy_pass http://realtime_backend;
        proxy_http_version 1.1;
        proxy_set_header Upgrade    $http_upgrade;
        proxy_set_header Connection $connection_upgrade;
        proxy_read_timeout 1h;                  # idle WebSockets must not be cut at 60 s
    }
}
```

## A receptionist forwarding calls

The receptionist (NGINX) takes every call and forwards it inside. Whether they read out the full extension or drop the department prefix depends on one small instruction, and for long conference calls (WebSockets) they must not hang up after a minute of silence.

**Quiz:** With `location /api/ { proxy_pass http://backend/; }`, what URI does the backend receive for /api/users?

- [ ] /api/users
- [ ] /backend/users
- [ ] /
- [x] /users

*Answer:* /users. Because proxy_pass includes a URI (/), the matched /api/ prefix is replaced by /.
