Nginx 的 location 路径匹配语法详解

198 阅读2分钟

本文系统梳理 location 的匹配规则、优先级顺序,并结合示例说明常见误区,帮助你在实际配置中做到可预测、可控

location 指令的匹配方式与优先级

Nginx 在接收到请求后,会按照固定的规则顺序location 进行匹配。
理解优先级,是正确配置的关键。

写法示例匹配方式优先级
精确匹配 =location = /fooURI 必须完全一致🥇 最高
前缀匹配 ^~location ^~ /images/前缀匹配,且命中后不再进入正则匹配阶段🥈 第二
正则匹配 ~location ~ .php$区分大小写的正则🥉 第三(正则中按书写顺序)
正则匹配 ~*location ~* .jpg$忽略大小写的正则同上
前缀匹配(普通)location /foo前缀匹配,多个命中时取最长前缀🏅 第四
通用匹配 /location /默认兜底最低

实际匹配流程(简化版)

可以用一句话概括:

先精确 → 再前缀 → 再正则 → 最后兜底

更完整的逻辑是:

  1. 先检查是否存在 精确匹配 (=)
  2. 再检查所有 前缀匹配(两种前缀),记录最长的一个
  3. 如果该前缀是 ^~,直接命中并结束
  4. 否则进入 正则匹配(按配置顺序)
  5. 若正则未命中,则回退到最长的普通前缀匹配

常见配置示例

server {
    # 1. 精确匹配:只匹配 /login
    location = /login {
        ...
    }

    # 2. 静态资源:前缀匹配并阻断正则
    location ^~ /static/ {
        root /web/data;
    }

    # 3. 正则匹配:处理 PHP 请求
    location ~ .php$ {
        fastcgi_pass unix:/run/php/php7.4-fpm.sock;
    }

    # 4. 普通前缀匹配:API 转发
    location /api {
        proxy_pass http://api-backend;
    }

    # 5. 默认兜底
    location / {
        index index.html;
    }
}

📍 实践建议

  • 静态资源路径(如 /static//assets/)优先使用 ^~
  • API、页面路由多使用普通前缀匹配
  • 正则匹配谨慎使用,避免性能和可读性问题

易错点:proxy_pass 的路径拼接规则 ⚠️

proxy_pass 结尾有 /:替换 location 前缀
proxy_pass 结尾无 /:保留原始 URI

裁剪前缀(推荐用于 API 网关)

location /api/ {
    proxy_pass http://backend/;
    proxy_set_header Host $host;
    proxy_set_header X-Real-IP $remote_addr;
}

# /api/user/list  →  http://backend/user/list

不裁剪前缀

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

# /api/user/list  →  http://backend/api/user/list

root vs alias

路径结构一致用 root
路径结构不一致用 alias

alias 三大坑:

  1. location 要带 /
  2. alias 要带 /
  3. 正则要写 $1

alias 可以配合 try_files 使用,但要理解 $uri 仍然是“原始 URI”,不会自动去掉 location 前缀。

对比表

项目rootalias
路径拼接root + 完整URIalias 替换 location 前缀
是否保留 location 前缀保留不保留
使用场景常规静态目录目录映射
正则 location不需要特殊处理必须用 $1

总结

  • location优先级不是配置顺序,而是语法规则
  • =^~ 是控制匹配行为的“利器”
  • 正则匹配应作为补充手段,而非主力方案
  • proxy_pass 是否带 /,直接决定请求路径是否被裁剪

参考