Nginx 反向代理怎么配:先搞懂 location、proxy_pass 尾斜杠和 root/alias

1次阅读
没有评论

写 Nginx 配置时,最容易出问题的地方往往不是“会不会启动”,而是路径被转发成了另一个样子:多了一级目录、少了前缀、出现双斜杠,或者静态文件明明存在却 404。

要把这类问题排清楚,先抓住三个点:location 怎么匹配,proxy_pass 尾斜杠怎么改写路径,rootalias 到底差在哪。

先看 Nginx 配置结构

Nginx 配置按上下文组织,常见层级可以这样记:

  • main:全局配置,比如 worker、pid、日志。
  • events:连接处理模型和连接数。
  • http:HTTP 服务、日志、压缩、缓存和代理。
  • server:一个虚拟主机。
  • location:某一类 URI 的处理规则。
  • stream:TCP / UDP 代理。

一个最小反向代理配置大概长这样:

worker_processes auto;

events {
    worker_connections 2048;
}

http {
    include mime.types;
    default_type application/octet-stream;

    upstream app_backend {
        server 127.0.0.1:8080 weight=10;
        server 127.0.0.1:8081 weight=10;
    }

    server {
        listen 80;
        server_name example.com;

        location / {
            proxy_pass http://app_backend;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
            proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
            proxy_set_header X-Forwarded-Proto $scheme;
        }
    }
}

真正上线时还要补日志、超时、缓存、安全和 HTTPS,但理解反向代理主线,先从这几块就够了。

location 匹配先看优先级

location 不是按配置文件里谁写在前面就一定谁生效。常见匹配方式有几类:

  • location = /abc {}:精确匹配,只匹配 /abc
  • location /abc {}:普通前缀匹配,可匹配 /abc/abc//abcd
  • location ^~ /static/ {}:前缀命中后停止继续匹配正则。
  • location ~ \.jpg$ {}:正则匹配,区分大小写。
  • location ~* \.jpg$ {}:正则匹配,不区分大小写。

优先级可以粗略记成:

  1. 先看精确匹配 =
  2. 再看最长前缀匹配,如果命中 ^~ 就停止。
  3. 再看正则匹配 ~~*
  4. 最后使用普通前缀匹配结果。

排障时不要只盯某一个 location,要确认请求实际命中了哪条规则。

proxy_pass 的尾斜杠最容易踩坑

proxy_pass 是否带 URI、是否以 / 结尾,会影响转发到后端的路径。

假设用户访问:

/test/xxoo.html

常见结果可以这样记:

  • location /test/ { proxy_pass http://upstream/; }:转到后端时路径通常变成 /xxoo.html
  • location /test/ { proxy_pass http://upstream; }:转到后端时路径通常保留 /test/xxoo.html
  • location /test/ { proxy_pass http://upstream/api/; }:转到后端时路径通常变成 /api/xxoo.html
  • location /test/ { proxy_pass http://upstream/api; }:很容易得到 /apixxoo.html 这种不是你想要的拼接结果。

所以,代理 API 时最好固定一种写法,不要混用。

比如你希望外部访问 /api/user,后端实际收到 /user,可以用:

location /api/ {
    proxy_pass http://backend/;
}

如果你希望后端也收到 /api/user,可以用:

location /api/ {
    proxy_pass http://backend;
}

这两种都可以,关键是团队要知道自己选的是哪一种。

root 和 alias 不是一回事

静态文件 404 时,rootalias 也是高频坑。

root 会把 location 匹配到的 URI 继续拼到根目录后面。

location /test/ {
    root /www/abc;
}

访问 /test/a.jpg 时,Nginx 会去找:

/www/abc/test/a.jpg

alias 则是用指定目录替换掉 location 前缀。

location /test/ {
    alias /www/abc/;
}

访问 /test/a.jpg 时,Nginx 会去找:

/www/abc/a.jpg

如果你本来想把 /static/ 映射到某个真实目录,通常要认真判断应该用 root 还是 alias。这里写错时,配置语法可能没问题,但线上就是找不到文件。

常用命令先记这几个

改配置前后,先养成检查和 reload 的习惯:

nginx -t          # 检查配置
nginx -s reload  # 重新加载配置
nginx -s quit    # 正常关闭
nginx -s stop    # 快速关闭
nginx -s reopen  # 重新打开日志文件

Homebrew 安装时常见路径:

配置文件:/usr/local/etc/nginx/nginx.conf
默认根目录:/usr/local/var/www
Apple Silicon 根目录:/opt/homebrew/var/www

不同安装方式路径可能不同,排障时可以先用 nginx -t 看它实际读取了哪份配置。

Gzip 和性能参数别一上来拉满

常见 Gzip 配置可以这样写:

gzip on;
gzip_disable "msie6";
gzip_proxied any;
gzip_min_length 1k;
gzip_comp_level 4;
gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;

注意三点:

  • 小文件压缩收益低,gzip_min_length 不要太小。
  • 图片、视频这类已压缩内容通常不需要再 gzip。
  • 压缩等级越高不一定越好,要看 CPU 和响应体大小。

常见性能参数也先从稳妥配置开始:

worker_processes auto;
worker_rlimit_nofile 10000;

events {
    worker_connections 2048;
    multi_accept on;
}

http {
    sendfile on;
    tcp_nopush on;
    tcp_nodelay on;
    keepalive_timeout 65;
    client_header_timeout 10;
    client_body_timeout 10;
    reset_timedout_connection on;
    send_timeout 30;
}

这些参数不是越大越好。比如 worker_connections 还要结合系统文件句柄上限、后端连接数、机器资源和业务峰值来看。

限流配置要先观察正常峰值

接口限流可以用 limit_reqlimit_conn

limit_req_zone $binary_remote_addr zone=per_ip_req:10m rate=20r/s;
limit_conn_zone $binary_remote_addr zone=per_ip_conn:10m;

server {
    location /api/ {
        limit_req zone=per_ip_req burst=5 nodelay;
        limit_conn per_ip_conn 20;
        proxy_pass http://app_backend;
    }
}

这里要注意:

  • 先看正常峰值,再定 rate 和连接数。
  • burst 允许短时突发。
  • nodelay 表示突发请求不排队等待,直接按规则处理。
  • 限流太紧会误伤正常用户,太松又挡不住异常流量。

排障顺序

如果 Nginx 反向代理不符合预期,可以按这个顺序查:

  1. 先跑 nginx -t,确认配置语法和实际配置文件路径。
  2. 看请求命中了哪个 server_namelocation
  3. 检查 proxy_pass 是否带尾斜杠,以及后端实际收到的路径。
  4. 静态文件 404 时,确认用了 root 还是 alias
  5. error.log,再用 access.log 分析状态码和上游耗时。
  6. 必要时临时加更细的日志字段,确认 upstream、URI 和转发头。

小结

Nginx 反向代理配置不难,但路径规则很容易让人误判。

可以先记住几句话:

  • location 要按匹配优先级看,不是只看文件顺序。
  • proxy_pass 带不带尾斜杠,会影响转发到后端的 URI。
  • root 是把 URI 拼到根目录后面,alias 是替换 URI 前缀。
  • Gzip、连接数和限流参数要结合实际流量,不要一上来写满。
  • 改配置先 nginx -t,再 reload,最后看日志确认请求真实走向。

把这几个点搞清楚,绝大多数 Nginx 反向代理和静态资源路径问题都会好排很多。

参考资料

正文完
 0
bdspAdmin
版权声明:本站原创文章,由 bdspAdmin 于2026-06-11发表,共计3737字。
转载说明:除特殊说明外本站文章皆由CC-4.0协议发布,转载请注明出处。
评论(没有评论)