nginx的rewrite
rewrite中的break和last两个指令用法基本相同,但含义不同,需要放到rewrite规则的末尾,用来控制重写后的链接是否继续被nginx配置执行(主要是rewrite、return指令)。编辑www.1.com.conf[root@k8s-node01 vhost]# vi www.1.com.confserver {listen 80;...
rewrite中的break和last
两个指令用法基本相同,但含义不同,需要放到rewrite规则的末尾,用来控制重写后的链接是否继续被nginx配置执行(主要是rewrite、return指令)。
编辑www.1.com.conf
[root@k8s-node01 vhost]# vi www.1.com.conf
server {
listen 80;
server_name www.1.com;
root /data/wwwroot/www.1.com;
rewrite_log on;
rewrite /1.html /2.html;
rewrite /2.html /3.html;
}
创建html文件
[root@k8s-node01 conf]# cd /data/wwwroot/www.1.com/
[root@k8s-node01 www.1.com]# vi 1.html
[root@k8s-node01 www.1.com]# vi 2.html
[root@k8s-node01 www.1.com]# vi 3.html
访问
[root@k8s-node01 vhost]# /usr/local/nginx/sbin/nginx -s reload
[root@k8s-node01 www.1.com]# curl -x127.0.0.1:80 www.1.com/1.html
333333333333333333
查看错误日志,最终访问到3.html
7.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:24:40 [notice] 16573#0: *2 rewritten data: "/2.html", args: "", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:24:40 [notice] 16573#0: *2 "/2.html" matches "/2.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:24:40 [notice] 16573#0: *2 rewritten data: "/3.html", args: "", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
加上break
server {
listen 80;
server_name www.1.com;
root /data/wwwroot/www.1.com;
rewrite_log on;
rewrite /1.html /2.html;break;
rewrite /2.html /3.html;
}
[root@k8s-node01 vhost]# /usr/local/nginx/sbin/nginx -s reload
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.1.com/1.html
22222222
#访问到2结束
#在这里break改为last效果一样
#当在local中使用时不一样
location
server {
listen 80;
server_name www.1.com;
root /data/wwwroot/www.1.com;
rewrite_log on;
location / {
rewrite /1.html /2.html;
rewrite /2.html /3.html;
}
location /2.html {
rewrite /2.html /a.html;
}
location /3.html {
rewrite /3.html /b.html;
}
}
[root@k8s-node01 logs]# curl -x127.0.0.1:80 www.1.com/1.html
<html>
<head><title>404 Not Found</title></head>
<body bgcolor="white">
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
2019/08/21 21:45:08 [notice] 16917#0: *6 "/1.html" matches "/1.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 rewritten data: "/2.html", args: "", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 "/2.html" matches "/2.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 rewritten data: "/3.html", args: "", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 "/3.html" matches "/3.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 rewritten data: "/b.html", args: "", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 "/1.html" does not match "/b.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [notice] 16917#0: *6 "/2.html" does not match "/b.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:45:08 [error] 16917#0: *6 open() "/data/wwwroot/www.1.com/b.html" failed (2: No such file or directory), client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
#//进入根,/1.html匹配到规则/1.html,转到/2.html。/2.html匹配到规则/2.html,转到/3.html。
#//3.html匹配到location /3.html,转到/b.html。/b.html跳出来进入根试图匹配规则/1.html,/2.html
#//最后报错
加break
server {
listen 80;
server_name www.1.com;
root /data/wwwroot/www.1.com;
rewrite_log on;
location / {
rewrite /1.html /2.html;break;
rewrite /2.html /3.html;
}
location /2.html {
rewrite /2.html /a.html;
}
location /3.html {
rewrite /3.html /b.html;
}
}
[root@k8s-node01 vhost]# /usr/local/nginx/sbin/nginx -s reload
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.1.com/1.html
22222222
#访问到www.2.com
2019/08/21 21:59:17 [notice] 17201#0: *7 "/1.html" matches "/1.html", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
2019/08/21 21:59:17 [notice] 17201#0: *7 rewritten data: "/2.html", args: "", client: 127.0.0.1, server: www.1.com, request: "GET HTTP://www.1.com/1.html HTTP/1.1", host: "www.1.com"
#即遇到break后面不再执行,如果改为last本次location不再执行,但后面依旧执行
rewrite中return
#//返回状态码
[root@k8s-node01 vhost]# vi default.conf
server {
listen 80 default_server;
return 403;
}
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 dlfkakf
<html>
<head><title>403 Forbidden</title></head>
<body bgcolor="white">
<center><h1>403 Forbidden</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
#//if中使用
[root@k8s-node01 vhost]# vi www.1.com.conf
server {
listen 80;
server_name www.1.com;
root /data/wwwroot/www.1.com;
rewrite_log on;
if ( $request_uri ~ "\.htpasswd|\.bak" )
{
return 404;
rewrite /(.*) /aaa.txt; #该行配置不会被执行。
}
}
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.1.com/.htppasswd
<html>
<head><title>404 Not Found</title></head>
<body bgcolor="white">
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
#//返回字符串
server{
listen 80;
server_name www.lsy.com;
return 200 "hello";
}
#//如果要想返回字符串,必须要加上状态码,否则会报错。
#//还可以支持json数据
location ^~ /lsy{
default_type application/json ;
return 200 '{"name":"lsy","id":"100"}';
}
#//也支持写一个变量
location /test {
return 200 "$host $request_uri";
}
#//返回url
server{
listen 80;
server_name www.lsy.com;
return http://www.lsylinux.com/123.html;
rewrite /(.*) /abc/$1; //该行配置不会被执行。
}
rewrite具体规则
格式:rewrite regex replacement [flag]
* rewrite配置可以在server、location以及if配置段内生效
* regex是用于匹配URI的正则表达式,其不会匹配到$host(域名)
* replacement是目标跳转的URI,可以以http://或者https://开头,也可以省略掉$host,直接写$request_uri部分(即请求的链接) * flag,用来设置rewrite对URI的处理行为,其中有break、last、rediect、permanent, rediect和permanent的区别在于,前者为临时重定向(302),而后者是永久重定向(301),对于用户通过浏览器访问,这两者的效果是一致的。 但是,对于搜索引擎蜘蛛爬虫来说就有区别了,使用301更有利于SEO。所以,建议replacemnet是以http://或者https://开头的flag使用permanent。
location / {
rewrite /(.*) http://www.lsy.com/$1 permanent;
}
#说明:.*为正则表达式,用()括起来,在后面的URI中可以调用它,第一次出现的()用$1调用,
#第二次出现的()用$2调用,以此类推。
location / {
rewrite /.* http://www.lsy.com$request_uri permanent;
}
#在replacement中,支持变量,这里的$request_uri就是客户端请求的链接
server{
listen 80;
server_name www.123.com;
root /tmp/123.com;
index index.html;
rewrite /(.*) /abc/$1 redirect;
}
#本例中的rewrite规则有问题,会造连续循环,最终会失败,解决该问题有两个方案。
#关于循环次数,经测试发现,curl 会循环50次,chrome会循环80次,IE会循环120次,firefox会循环20次。
#测试
[root@k8s-node01 vhost]# vi www.2.com.conf
server {
listen 80;
server_name www.2.com;
root /data/wwwroot/www.2.com;
location /
{
rewrite /(.*) /abc/$1 redirect;
}
}
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.2.com
<html>
<head><title>302 Found</title></head>
<body bgcolor="white">
<center><h1>302 Found</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.2.com -L
curl: (47) Maximum (50) redirects followed
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.2.com -I
HTTP/1.1 302 Moved Temporarily
Server: nginx/1.14.0
Date: Tue, 27 Aug 2019 15:11:36 GMT
Content-Type: text/html
Content-Length: 161
Location: http://www.2.com/abc/
Connection: keep-alive
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 www.2.com/abc -I
HTTP/1.1 302 Moved Temporarily
Server: nginx/1.14.0
Date: Tue, 27 Aug 2019 15:12:01 GMT
Content-Type: text/html
Content-Length: 161
Location: http://www.2.com/abc/abc
Connection: keep-alive
#解决
server{
listen 80;
server_name www.123.com;
root /tmp/123.com;
index index.html;
rewrite /(.*) /abc/$1 break;
}
#在rewrite中使用break,会避免循环。
server{
listen 80;
server_name www.123.com;
root /tmp/123.com;
index index.html;
if ($request_uri !~ '^/abc/')
{
rewrite /(.*) /abc/$1 redirect;
}
}
#加一个条件限制,也可以避免产生循环
rewrite常用举例
域名跳转
# 不带条件的
server{
listen 80;
server_name www.lsylinux.com;
rewrite /(.*) http://www.lsy.com/$1 permanent;
.......
}
#带条件的
server{
listen 80;
server_name www.lsylinux.com aminglinux.com;
if ($host != 'www.lsylinux.com')
{
rewrite /(.*) http://www.lsylinux.com/$1 permanent;
}
.......
}
#http跳转到https
server{
listen 80;
server_name www.lsylinux.com;
rewrite /(.*) https://www.aminglinux.com/$1 permanent;
.......
}
#域名访问二级目录
server{
listen 80;
server_name bbs.lsylinux.com;
rewrite /(.*) http://www.lsylinux.com/bbs/$1 last;
.......
}
#静态请求分离
server{
listen 80;
server_name www.lsylinux.com;
location ~* ^.+.(jpg|jpeg|gif|css|png|js)$
{
rewrite /(.*) http://img.lsylinux.com/$1 permanent;
}
.......
}
#或者
server{
listen 80;
server_name www.lsylinux.com;
if ( $uri ~* 'jpg|jpeg|gif|css|png|js$')
{
rewrite /(.*) http://img.lsylinux.com/$1 permanent;
}
.......
}
防盗链
server{
listen 80;
server_name www.lsylinux.com;
location ~* ^.+.(jpg|jpeg|gif|css|png|js|rar|zip|flv)$
{
valid_referers none blocked server_names *.lsylinux.com lsylinux.com *.lsy.com lsy.com;
if ($invalid_referer)
{
rewrite /(.*) http://img.lsylinux.com/images/forbidden.png;
}
}
.......
}
# *这里是通配,跟正则里面的*不是一个意思,none指的是referer不存在的情况(curl -e 测试),
# blocked指的是referer头部的值被防火墙或者代理服务器删除或者伪装的情况,
# 该情况下,referer头部的值不以http://或者https://开头(curl -e 后面跟的referer不以http://或者# https://开头)。
# 或者
location ~* ^.+.(jpg|jpeg|gif|css|png|js|rar|zip|flv)$
{
valid_referers none blocked server_names *.lsylinux.com *.lsy.com lsylinux.com lsy.com;
if ($invalid_referer)
{
return 403;
}
}
伪静态
location / {
rewrite ^([^\.]*)/topic-(.+)\.html$ $1/portal.php?mod=topic&topic=$2 last;
rewrite ^([^\.]*)/forum-(\w+)-([0-9]+)\.html$ $1/forum.php?mod=forumdisplay&fid=$2&page=$3 last;
rewrite ^([^\.]*)/thread-([0-9]+)-([0-9]+)-([0-9]+)\.html$ $1/forum.php?mod=viewthread&tid=$2&extra=page%3D$4&page=$3 last;
rewrite ^([^\.]*)/group-([0-9]+)-([0-9]+)\.html$ $1/forum.php?mod=group&fid=$2&page=$3 last;
rewrite ^([^\.]*)/space-(username|uid)-(.+)\.html$ $1/home.php?mod=space&$2=$3 last;
rewrite ^([^\.]*)/(fid|tid)-([0-9]+)\.html$ $1/index.php?action=$2&value=$3 last;
}
rewrite多个条件的并且
#//nginx里面if不能嵌套
server {
listen 80;
server_name www.1.com;
root /data/wwwroot/www.1.com;
rewrite_log on;
set $tmp 0;
if ( $request_uri !~ "^/abc/" )
{
set $tmp "${tmp}1";
}
if ( $http_user_agent ~ 'IE|chrome' )
{
set $tmp "${tmp}2";
}
if ( $tmp = "012" )
{
return 406;
}}
#// -A 模拟浏览器
[root@k8s-node01 vhost]# /usr/local/nginx/sbin/nginx -s reload
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 -A "dlkfakfchromefjoe" www.1.com/1.html
<html>
<head><title>406 Not Acceptable</title></head>
<body bgcolor="white">
<center><h1>406 Not Acceptable</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 -A "dlkfakfchromefjoe" www.1.com/abc/1.html
<html>
<head><title>404 Not Found</title></head>
<body bgcolor="white">
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
[root@k8s-node01 vhost]# curl -x127.0.0.1:80 -A "dlkfakfchrddomefjoe" www.1.com/abc/1.html
<html>
<head><title>404 Not Found</title></head>
<body bgcolor="white">
<center><h1>404 Not Found</h1></center>
<hr><center>nginx/1.14.0</center>
</body>
</html>
更多推荐
所有评论(0)