前言
在Nginx配置中,重定向时查询参数的处理是个老大难问题。很多人配完301跳转,发现UTM参数、分页参数全丢了,流量追踪数据凭空消失。Nginx提供了多种参数保留方式,用错了轻则参数丢失,重则循环重定向。这篇文章把四种主流方法掰开了揉碎了讲,帮你彻底搞懂什么时候该用哪种。
方法一:直接用$request_uri —— 最偷懒的完整保留
这是最简单粗暴的方式,$request_uri本身包含原始请求的完整URI(带查询字符串),直接拿来拼接跳转目标就行。
```nginx server { listen 80; server_name example.com; # HTTP强跳HTTPS,查询参数完整保留 return 301 https://example.com$request_uri; } ```实测效果:访问 http://example.com/page?id=5&page=2 会直接跳转到 https://example.com/page?id=5&page=2,参数一个不落。
适用场景:整站HTTP→HTTPS迁移、所有路径统一跳转。简单直观,不容易出错。
缺点:完全照搬原参数,无法做二次加工——比如你想删掉fbclid这种追踪垃圾参数,这种方式就做不到。
方法二:$uri$is_args$args —— 可干预的精准拼接
当你需要对查询参数做进一步处理时,就得把参数拆开来看了。Nginx提供了三个变量:
- $uri:解码后的路径部分,不含查询字符串
- $is_args:如果有查询参数则返回"?",否则返回空字符串
- $args:原始查询参数字符串
这里要注意:$args不含前导问号,所以要用$is_args$args组合来判断是否需要加问号。实测?a=1&b=2时$is_args返回"?",$args返回"a=1&b=2",拼接起来正好。
适用场景:需要筛选参数、添加额外追踪标记的场景。
方法三:map指令 —— 批量过滤追踪参数
如果你想统一过滤掉fbclid、gclid这类垃圾参数,每次手写if判断太累。map指令可以批量处理——在http块定义映射规则,然后按需调用。
```nginx http { # 定义需要过滤的追踪参数 map $args $clean_args { default $args; # 包含fbclid则删除该参数 "~*(^|&)fbclid=[^&]*(&.*)?$" "$2"; "~*(^|&)gclid=[^&]*(&.*)?$" "$2"; # ...可继续追加 } # 去掉尾部空参数(处理上面正则产生的末尾&) map $clean_args $final_args { default $clean_args; "~*(&)$" "$1"; } } server { listen 80; # 用过滤后的参数做跳转 return 301 https://example.com$uri$is_args$final_args; } ```这种方式灵活性强,维护成本低。要加新的过滤参数直接在map里加一行正则就行。
适用场景:大量域名统一管理、标准化参数过滤策略。
方法四:rewrite配合last/break —— 带条件的精确跳转
当你需要根据特定条件选择不同的跳转目标时,rewrite配合flag可以实现更复杂的逻辑。
```nginx server { listen 80; # 带问号的rewrite会覆盖原查询字符串 # 所以要保留参数得显式拼回来 rewrite ^/old-page/(.*)$ https://example.com/new-page/$1?$args? last; # 不用last就继续往下走,不会重复匹配 } ```rewrite有一个容易踩的坑:目标URL带问号会清空原查询字符串。比如写 rewrite ^ /target? flag; 问号后面没东西,原参数就全丢了。如果想保留,必须写成 rewrite ^ /target?$args? flag; 或者配合 $is_args。
四种方法横向对比
| 方法 | 参数保留 | 灵活性 | 维护难度 | 适用场景 | |------|---------|--------|---------|---------| | $request_uri直接用 | 完整保留 | 低 | 最简单 | 整站迁移、简单跳转 | | $uri$is_args$args拼接 | 可干预 | 中 | 中等 | 追加参数、条件筛选 | | map指令批量过滤 | 选择性保留 | 高 | 需配置基础 | 多域名统一管理 | | rewrite+last/break | 可编程 | 高 | 复杂 | 条件分支、复杂路径映射 |避坑提示
- **问号重复**:拼接URL时避免写成
$uri??$args,双问号会导致参数解析异常 - **参数编码**:$args是编码后的原始字符串,$request_uri同理,如有特殊字符要确认编码是否一致
- **循环重定向**:条件判断没写好会导致多重跳转循环,用
nginx -T看完整配置链路 - **测试命令**:用
curl -I -L --max-redirs 0 http://example.com/path?a=1追踪每次跳转的参数变化
结语
参数保留没有万能公式,取决于你的业务场景。简单整站迁移用$request_uri最省事;需要过滤追踪参数用map指令省心省力;涉及多域名多策略的配合场景,才需要上rewrite+条件判断。搞清楚四种方法的能力边界,重定向时参数丢失的问题基本就能绝迹了。
相关文章:
版权声明
本文仅代表个人观点。
本文系AI辅助作者原创,未经许可,转载请保留原文链接。

发表评论