Nginx配置指令Rewrite04
Nginx配置指令Rewrite
Rewrite功能配置
Rewrite功能是Nginx服务器提供的一个重要基本功能, 主要用于实现URL的重写. 其具体实现需要依赖PCRE的支持, Nginx通过 ngx_http_rewrite_module 模块解析处理Rewrite功能相关配置
1 | 文档: http://nginx.org/en/docs/http/ngx_http_rewrite_module.html |
Rewrite相关命令
set
用于设置一个Nginx变量, 可用于 server/location/if 块中
指令格式
set $variable value
variables: 变量的名称. 该变量名要用 $ 作为变量开头, 且不能与nginx全局变量同名
value: 变量的值.
Nginx常用全局变量
1 | 请求: http://192.168.200.133/server?arg1=value1&arg2=value2 |
| 变量名 | 说明 |
|---|---|
| $args | 请求URL中参数, 功能与 $query_string 一样“ arg1=value1&arg2=value2“ |
| $http_user_agent | 用户访问客户端或代理的信息, 同Request Headers->User-Agent |
| $host | 服务器的server_name 值“ 192.168.200.133“ |
| $document_uri | 当前访问地址的URI, 功能与 $uri 一样“ /server“ |
| $content_length | 请求头中的 Content-Length 值 |
| $content_type | 请求头中的 Content-Type 值 |
| $http_cookie | 客户端的cookie信息 |
| $limit_rate | Nginx服务器对网络连接速率的限制, 默认为0, 不限制 |
| $remote_addr | 客户端的IP地址 |
| $remote_port | 客户端与服务端连接的端口号 |
| $remote_user | 客户端的用户名, 需要认证模块 |
| $scheme | 访问协议 |
| $server_addr | 服务端的地址 |
| $server_name | 服务端的名称 |
| $server_port | 服务端的端口 |
| $server_protocol | 客户端请求协议版本 |
| $request_body_file | 发给服务器的本地资源名称 |
| $request_method | 客户端的请求方式 |
| $request_filename | 当前请求资源文件的路径名 |
| $request_uri | 当前请求的URI, 且携带请求参数 “ /server?arg1=value1&arg2=value2“ |
if
用于支持条件判断, 根据不同记过选择不同Nginx配置, 可用于server/location 块中
指令格式
if (condition){...}
注意: if后必须带一个空格
condition: 判定条件, 支持一下写法:
1 | 1.变量名. 如果变量对应值为空字符串或0, if判断都为false, 其余情况均为true |
break
1.用于中断当前作用域的其他nginx配置. 在同一作用域中, break之后的配置不再执行生效
2.终止当前匹配并将当前URI在本location中进行301重定向访问
指令格式
break;
使用案例
访问: http://test.project.com:8081/testbreak
1 | location /testbreak{ |
1 | 同时创建目录 /var/www/test/testbreak, 创建文件 /var/www/test/testbreak/break.html |
显示结果如下, break不仅中断了本作用域的 set $username number3; 配置, 而且301永久重定向到了本location下的root+index配置页面

return
用于完成对请求的处理, 直接向客户端返回. 在return后的所有Nginx配置都无效
指令格式
return code [text]; || return code URL; || return URL;
code: 返回客户端的HTTP状态, 0-999
text: 返回客户端的响应体内容, 支持变量使用
URL: 返回给客户端的URL地址 (302跳转)
1 | location /testreturn{ |
rewrite
通过正则表达式改变URI. 可以同时存在多个指令, Nginx按照顺序依次执行匹配
指令格式
rewrite regex replacement [flag]
regex: 用来匹配URI的正则表达式
replacement: 匹配成功后, 用于替换URI内容的字符串. 若该配置以 http:// 或 https:// 开头, 则不会继续执行其他rewrite, 直接返回重写后的URI给客户端
flag: 用于设置rewrite对URI的处理行为, 有如下值:
1 | last - 终止继续在本location块中处理接收到的URI, 并将此处重写的URI作为一个新的URI, 使用各location块进行处理. 该标识将重写后的URI重新载server块中执行, 为重写后的URI提供了在其他location块中执行的机会, 不会修改当前浏览器的URL |
使用案例
1 | location /rewrite{ |
访问 http://test.project.com:8081/rewrite/urlxxx

访问 http://test.project.com:8081/rewrite/testxxx

rewrite_log
开启URL重写日志的输出功能, 可用于http/server/location/if
指令语法
rewrite_log on|off;
开启后,URL重写日志将会以notice级别输出到error_log中
1 | rewrite_log on; |
日志数据如下:

Rewrite应用场景
域名跳转
访问京东商城, 可以使用www.jd.com , 也可以使用www.360buy.com , 除了单server块指定多server_name外, 还可以利用Rewrite实现该效果
1 | 准备三个域名 |
编写nginx配置文件
1 | server{ |
访问域名 http://test1.project.com/getUser/id?test=111

独立域名
一个完整项目包含多个模块, 如何为每个模块设置独立域名
1 | 需求为: |
编写nginx配置文件
1 | server{ |
访问效果如下



域名镜像
域名跳转部分中, 我们将test1.project.com和test2.project.com 均跳转到test.project.com, 即两个备份域名跳转到主域名, 如果不想把整个网站都做镜像, 仅为其中一个子目录下的资源做镜像, 可以在location块中配置Rewrite实现
1 | server{ |
访问效果如下:


目录自动添加”/“
创建nginx配置如下
1 | root /var/www/test; |
访问网址 http://test.project.com/goods, 显示如下:

可见可以访问, 但实际上是nginx做了301转发, 实际是去找root+index 文件展示出来
1 | nginx配置中的server_name_in_redirect, 在Nginx 0.8.48版本之前, 默认为on, 之后为off |
可以通过Rewrite在URI后面手动加/解决问题
修改nginx配置为:
1 | root /var/www/test; |
即可正常访问
合并目录
SEO要求包含URL的目录层级不要超过三层, 可以使用Rewrite简化输入目录层级
如: 需要访问服务器中的URI/server/11/22/33/44/55.html, 则完整URL应该是http://test.project.com/server/11/22/33/44/55.html, 在Rewrite后可以访问http://test.project.com/server-11-22-33-44/55.html 达成同样效果
1 | server{ |
访问效果如下

防盗链
当访问来源非授权时, 可以通过Rewrite到一张自定义图片资源上
1 | location /images{ |