--Nginx全局變量、rewrite實(shí)戰(zhàn)、nginx的location配置
一、nginx全局變量
nginx 主配置文件中的log_format,常用全局變量:
https://github.com/aminglinux/nginx/blob/master/rewrite/variable.md
變量
說(shuō)明
$args
請(qǐng)求中的參數(shù),如www.123.com/1.php?a=1&b=2的$args就是a=1&b=2
$body_bytes_sent
服務(wù)器發(fā)送給客戶端的響應(yīng)body字節(jié)數(shù)
$content_length
HTTP請(qǐng)求信息里的"Content-Length"
$conten_type
HTTP請(qǐng)求信息里的"Content-Type"
$document_root
nginx虛擬主機(jī)配置文件中的root參數(shù)對(duì)應(yīng)的值
$document_uri
當(dāng)前請(qǐng)求中不包含指令的URI,如www.123.com/1.php?a=1&b=2的$document_uri就是1.php,不包含后面的參數(shù)
$http_referer
記錄此次請(qǐng)求是從哪個(gè)連接訪問(wèn)過(guò)來(lái)的,可以根據(jù)該參數(shù)進(jìn)行防盜鏈設(shè)置
$host
主機(jī)頭,也就是域名
$http_user_agent
客戶端的詳細(xì)信息,也就是瀏覽器的標(biāo)識(shí),用curl -A可以指定
$http_cookie
客戶端的cookie信息
$http_x_forwarded_for
當(dāng)前端有代理服務(wù)器時(shí),設(shè)置web節(jié)點(diǎn)記錄客戶端地址的配置,此參數(shù)生效的前提是代理服務(wù)器也要進(jìn)行相關(guān)的x_forwarded_for設(shè)置
$limit_rate
如果nginx服務(wù)器使用limit_rate配置了顯示網(wǎng)絡(luò)速率,則會(huì)顯示,如果沒(méi)有設(shè)置, 則顯示0
$remote_addr
客戶端的公網(wǎng)ip
$remote_port
客戶端的port
$remote_user
如果nginx有配置認(rèn)證,該變量代表客戶端認(rèn)證的用戶名
$request
請(qǐng)求的URI和HTTP協(xié)議,如“GET /article-10000.html HTTP/1.1”
$request_body_file
做反向代理時(shí)發(fā)給后端服務(wù)器的本地資源的名稱
$request_method
請(qǐng)求資源的方式,GET/PUT/DELETE等
$request_filename
當(dāng)前請(qǐng)求的資源文件的路徑名稱,相當(dāng)于是$document_root/$document_uri的組合
$request_uri
請(qǐng)求的鏈接,包括$document_uri和$args
$scheme
請(qǐng)求的協(xié)議,如ftp,http,https
$server_protocol
客戶端請(qǐng)求資源使用的協(xié)議的版本,如HTTP/1.0,HTTP/1.1,HTTP/2.0等
$server_addr
服務(wù)器IP地址
$server_name
服務(wù)器的主機(jī)名
$server_port
服務(wù)器的端口號(hào)
$status
http狀態(tài)碼,記錄請(qǐng)求返回的狀態(tài)碼,例如:200、301、404等
$uri
和$document_uri相同
$http_referer
客戶端請(qǐng)求時(shí)的referer,通俗講就是該請(qǐng)求是通過(guò)哪個(gè)鏈接跳過(guò)來(lái)的,用curl -e可以指定
$time_local
記錄訪問(wèn)時(shí)間與時(shí)區(qū),如18/Jul/2014:17:00:01 +0800
二、rewrite實(shí)戰(zhàn)
域名跳轉(zhuǎn)(域名重定向)
示例1(不帶條件的):
server{
listen 80;
server_name www.a.com;
root /data/wwwroot/www.a.com;
index index.html;
rewrite /(.*) http://www.b.com/$1 permanent;
}
訪問(wèn)a.com跳轉(zhuǎn)到b.com
示例2(帶條件的):
server{
listen 80;
server_name www.a.com a.com;
root /data/wwwroot/www.a.com;
index index.html;
if ($host != 'www.a.com')
{
rewrite /(.*) http://www.a.com/$1 permanent;
}
}
通過(guò)判斷條件,如果$host不等于www.a.com的,跳轉(zhuǎn)到www.a.com
示例3(http跳轉(zhuǎn)到https):
server{
listen 80;
server_name www.a.com;
root /data/wwwroot/www.a.com;
index index.html;
rewrite /(.*) https://www.a.com/$1 permanent;
}
示例4(域名訪問(wèn)二級(jí)目錄)
server{
listen 80;
server_name blog.a.com;
index index.html;
rewrite /(.*) http://www.a.com/blog/$1 permanent;
}
示例5(靜態(tài)請(qǐng)求分離)
server{
listen 80;
server_name www.a.com;
location ~* ^.+.(jpg|jpeg|gif|css|png|js)$
{
rewrite /(.*) http://img.a.com/$1 permanent;
}
}
或者:
server{
listen 80;
server_name www.a.com;
index index.html;
if ( $uri ~* 'jpg|jpeg|gif|css|png|js$')
{
rewrite /(.*) http://img.a.com/$1 permanent;
}
}
防盜鏈
示例6
server{
listen 80;
server_name www.a.com;
location ~* ^.+.(jpg|jpeg|gif|css|png|js|rar|zip|flv)$
{
valid_referers none blocked server_names *.a.com a.com *.tobe.com tobe.com;
if ($invalid_referer)
{
rewrite /(.*) http://img.a.com/images/forbidden.png;
}
}
.......
}
說(shuō)明:這里是通配,跟正則里面的不是一個(gè)意思,valid_referers定義白名單,none指的是referer不存在、為空的情況(curl -e 測(cè)試),
blocked指的是referer頭部的值被防火墻或者代理服務(wù)器刪除或者偽裝的情況,
該情況下,referer頭部的值不以http://或者h(yuǎn)ttps://開(kāi)頭(curl -e 后面跟的referer不以http://或者h(yuǎn)ttps://開(kāi)頭)。
或者:
location ~* ^.+.(jpg|jpeg|gif|css|png|js|rar|zip|flv)$
{
valid_referers none blocked server_names *.a.com *.tobe.com a.com tobe.com;
if ($invalid_referer)
{
return 403;
}
}
偽靜態(tài)
示例7(discuz偽靜態(tài)):
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多個(gè)條件的并且
示例8:
location /{
set $rule 0; #值為0
if ($document_uri !~ '^/abc') #!~不匹配以abc開(kāi)頭的
{
set $rule "${rule}1"; #01
}
if ($http_user_agent ~* 'ie6|firefox')
{
set $rule "${rule}2"; #012
}
if ($rule = "012")
{
rewrite /(.*) /abc/$1 redirect;
}
}
當(dāng)滿足兩個(gè)條件不以abc開(kāi)頭,并且http_user_agent為ie6或firefox時(shí),跳轉(zhuǎn)到http://www.a.com/aaa/,不滿足其中的一個(gè)條件時(shí),返回了404
三、nginx的location配置
安裝第三方模塊echo-nginx-module
cd /usr/local/src/
git clone https://github.com/openresty/echo-nginx-module.git
nginx編譯安裝后的操作:
cd /usr/local/src/nginx-1.16.1
重新編譯
./configure --prefix=/usr/local/nginx --add-module=/usr/local/src/echo-nginx-module
make && make install
/usr/local/nginx/sbin/nginx -V
測(cè)試中使用,可以在虛擬主機(jī)配置文件中直接使用,如:echo 123;
location語(yǔ)法:
nginx location語(yǔ)法規(guī)則:location [=|~|~*|^~] /uri/ { … }
nginx的location匹配的變量是$uri
符號(hào)說(shuō)明=表示精確匹配^~表示uri以指定字符或字符串開(kāi)頭~表示區(qū)分大小寫(xiě)的正則匹配~*表示不區(qū)分大小寫(xiě)的正則匹配/通用匹配,任何請(qǐng)求都會(huì)匹配到
規(guī)則優(yōu)先級(jí):
= 高于 ^~ 高于 ~* 等于 ~ 高于 /
規(guī)則示例:
location = "/12.jpg" { ... }
如:
www.a.com/12.jpg 匹配
www.a.com/abc/12.jpg 不匹配
location ^~ "/abc/" { ... }
如:
www.a.com/abc/123.html 匹配
www.a.com/a/abc/123.jpg 不匹配
location ~ "png" { ... }
如:
www.a.com/aaa/bbb/ccc/123.png 匹配
www.a.com/aaa/png/123.html 匹配
location ~* "png" { ... }
如:
www.a.com/aaa/bbb/ccc/123.PNG 匹配
www.a.com/aaa/png/123.html 匹配
location /admin/ { ... }
如:
www.a.com/admin/aaa/1.php 匹配
www.a.com/123/admin/1.php 不匹配
小常識(shí):
有些資料上介紹location支持不匹配 !~,
如: location !~ 'png'{ ... }
這是錯(cuò)誤的,location不支持 !~
如果有這樣的需求,可以通過(guò)if來(lái)實(shí)現(xiàn),
如: if ($uri !~ 'png') { ... }
注意:location優(yōu)先級(jí)小于if