摘要:如果狀態碼附帶文字段落,該文本將被放置在響應主體。相反,如果狀態碼后面是一個,該將成為頭部值。沒有狀態碼的將被視為一個狀態碼,這種情況下需要以或者開頭。因為和不能簡單的只返回狀態碼,還必須有重定向的,這就是指令無法返回的原因了。
HTTP模塊(核心模塊,也是主要用到的模塊) server模塊
server模塊是http的子模塊,它用來定義一個虛擬主機
例子:
server { listen 80; server_name localhost www.example.com; root /Users/yangyi/www;# 全局定義,表示在該server下web的根目錄 index index.php index.html index.htm; charset utf-8; access_log logs/host.access.log main; #用來指定此虛擬主機的訪問日志存放路徑,輸出格式為main。 error_log logs/host.error.log error; #錯誤日志存放路徑,輸出格式為error。 error_page 404 /404.html; #狀態碼為404時的時候的網頁地址,還可定義500,502之類的 .... }
以上一些配置為在該server下具有全局性,例如 root,可在location中重新定義root
關于server_name用來指定IP地址或者域名,多個域名之間用空格分開
當我們想定義多個server監聽同一個端口但訪問的host不一樣時,server_name就派上用場了。nginx會根據HTTP請求的header Host選擇nginx配置文件里符合條件的server_name的server配置
匹配順序如下
完全匹配的server_name;
后綴匹配: *.example.com;
前綴匹配: www.example.*;
正則匹配: ~w+.com;
listen指令里配置了default或default_server的server;如`listen 80 default`
第一個匹配上listen的server。
所以當我們監聽的的端口只有一個server配置的時候,server_name 可以不填
關于root和alias的區別兩者作用差不多,區別在于最終映射的地址不同,例:
location /request_path/image/ { # 如果現在訪問 /request_path/image/a/b.jpg,root映 # 射的地址為/local_path/image/request_path/image/a/b.jpg, # 而alias為/local_path/image/a/b.jpg root /local_path/image/; alias /local_path/image/; }關于error_page
語法:error_page code ... [=[response]] uri
使用字段: http, server, location, if in location
產生的效果為內部跳轉(internal redirect),即用戶頁面地址不變,但內容實際上為設置的uri對應的內容
我們也可以自定義設置返回的狀態碼,如:
error_page 502 503 =200 /50x.html;
這樣用戶訪問產生502 、503的時候給用戶的返回狀態是200,內容是50x.html。
還有一種寫法是 = 后面不帶狀態碼,是針對相應的內容不是一個靜態的頁面,最終返回的狀態碼取決于對應url服務返回的狀態碼。
最主要和最復雜的配置,通過定位和解析url,判斷該選擇什么配置,支持正則和條件判斷;
簡單例子,匹配所有請求
location / { root /home/www/html; index index.php index.html index.htm; }
一個正則匹配的例子:
# 匹配.php結尾的請求 location ~ .php$ { .... }
一個反向代理的例子:
# 匹配到/api開頭的路由時候,將請求轉發到http://192.168.0.1,但是通常不是直接填寫地址,而是設置一個`upstream`配置,后面會提到 location /api { proxy_pass http://192.168.0.1; #請求轉向地址192.168.0.1 #不修改被代理服務器返回的響應頭中的location頭 proxy_redirect off; #使用nginx反向代理后,如果要使服務獲取真實的用戶信息,用以下的設置 proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; }
vue-router、react-router等路由框架要開啟history模式可以選擇的nginx配置的例子
location / { alias static/; try_files $uri $uri/ /index.html; }
location的匹配規則和順序
第一種是 = 類型,表示精確匹配,優先級最高,一旦匹配到忽略之后的正則匹配
^~ 類型,表示前綴匹配,是字符串開頭匹配而非正則匹配,當匹配到該規則時,停止往下面的搜索,所以如果存在兩個^~ 匹配的時候要注意有順序之分。優先級比正則高。
~ 和 ~*,正則匹配,兩者區別是后者不區分大小寫。有順序之分,匹配到第一個正則停止搜索。
/uri,普通字符串匹配,無順序之分,會選擇匹配長度最長的配置。
/ 通用匹配,匹配所有請求
還有一種特殊匹配類型 @url,只用于nginx內部跳轉,例:
location / { root /var/www/html; error_page 404 @40x; } location @40x { root /var/www/errors/40x.html; }upstream模塊
upstream后端服務器提供簡單的負載均衡(輪循調度和客戶端 IP)。
例子:
upstream backend { server backend1.example.com weight=5; server backend2.example.com:8080; server unix:/tmp/backend3; } server { location / { proxy_pass http://backend; } }
有常用兩種負載均衡支持調度算法,分別是 weight 和 ip_hash 。weight 模式下可以為每個 server 設置weight值,weight值越大,分配到的訪問機率越高,ip_hash 為同一個ip的
分配同一個后端服務器,這樣我們不用解決session共享問題。
include指令 使nginx配置更加靈活,將部分配置直接拆分出來,分成不同的配置文件
例子:
http { include mime.types; include vhost/*.conf; # 虛擬主機配置 }關于 mime.types:
mime type 和 文件擴展名的對應關系一般放在 mime.types 里,然后 用 include mime.types;
mime.types作用:通過文件的擴展名設置了Content-Type,Nginx如果沒找到對應文件的擴展名的話,就使用默認的Type,默認Type通用 default_type 定義,比如 default_type application/octet-stream ;
完整的 mime.types 配置:https://github.com/h5bp/server-configs-nginx/blob/master/mime.types
一個虛擬主機對一個文件配置,放到vhost文件夾下面,然后通過include指令包含進來,這樣更便于維護和管理
gzipgzip 壓縮,用來對靜態資源進行壓縮,需要客戶端同時支持才有效。
配置:
http { #開啟gzip壓縮 gzip on; #IE6的某些版本對gzip的壓縮支持很不好,故關閉 gzip_disable "MSIE [1-6].(?!.*SV1)"; #HTTP1.0以上的版本都啟動gzip gzip_http_version 1.0; #指定哪些類型的相應才啟用gzip壓縮,多個用空格分隔 gzip_types application/javascript application/json text/css text/plain; # 壓縮等級,可選1-9,值越大壓縮時間越長壓縮率越高, # 通常選5,能壓縮到原來的1/4 gzip_comp_level 5; }rewrite模塊(ngx_http_rewrite_mode)
rewrite模塊配合很多模塊一起使用,包含幾個指令:
break
if
return
rewrite
rewrite_log
set
uninitialized_variable_warn
這里簡單介紹下break、if、return,重點介紹 rewrite
break語法: break;
使用字段: server, location, if
此指令的意思是停止執行當前虛擬主機的后續rewrite指令集
例子
# 如果訪問的文件名不存在,反向代理到localhost 。這里的break也是停止rewrite檢查 if (!-f $request_filename) { break; proxy_pass http://127.0.0.1; }if
語法: if (condition) { ... }
使用字段: server, location
if 判斷一個條件,如果條件成立,則后面的大括號內的語句將執行,相關配置從上級繼承。
條件(conditon)可以是如下任何操作:
當表達式只是一個變量時,如果值為空或任何以0開頭的字符串都會當做false;
使用“=”和“!=”比較一個變量和字符串;
使用“~”做正則表達式匹配,“~*”做不區分大小寫的正則匹配,“!~”做區分大小寫的正則不匹配;
使用“-f”和“!-f” 檢查一個文件是否存在;
使用“-d”和“!-d”檢查一個目錄是否存在;
使用“-e”和“!-e”檢查一個文件、目錄、符號鏈接是否存在;
使用“-x”和“ !-x”檢查一個文件是否可執行;
# 如果提交方法為POST,則返回狀態405(Method not allowed) if ($request_method = POST) { return 405; }return
語法: return code [text];
return code URL;
return URL;
使用字段: server, location, if
停止處理并為客戶端返回狀態碼,非標準的444狀態碼將關閉連接,不發送任何響應頭。可以使用的狀態碼有:204,400,402-406,408,410, 411, 413, 416與500-504。如果狀態碼附帶文字段落,該文本將被放置在響應主體。相反,如果狀態碼后面是一個URL,該URL將成為location頭部值。沒有狀態碼的URL將被視為一個302狀態碼,這種情況下URL需要以“http://”, “https://”, 或者 “$scheme”開頭。
語法: rewrite regex replacement [flag];
使用字段: server, location, if
使用nginx提供的全局變量或自己設置的變量,然后結合正則表達式和標志位實現url重寫以及重定向。多條 rewrite 順序靠前且匹配的優先執行。可以通過設置 flag 停止繼續處理。如果replacement 以“http://”, “https://”, 或者 “$scheme”開頭,那么將立即停止處理并臨時重定向給客戶端。
flag可以是如下參數:
last,完成該rewrite規則的執行后,停止處理后續rewrite指令集;然后查找匹配改變后URI的新location;
break,完成該rewrite規則的執行后,停止處理后續rewrite指令集,并不再重新查找;但是當前location內剩余非rewrite語句和location外的的非rewrite語句可以執行;
redirect,返回302臨時重定向,地址欄會顯示跳轉后的地址;
permanent,返回301永久重定向,地址欄會顯示跳轉后的地址;即表示如果客戶端不清理瀏覽器緩存,那么返回的結果將永久保存在客戶端瀏覽器中了。
因為301和302不能簡單的只返回狀態碼,還必須有重定向的URL,這就是return指令無法返回301,302的原因了。兩種重定向的方式對客戶端來說是一樣的,就是重新加載另外一個url。我們在實際設置中推薦只使用永久重定向,因為臨時重定向可能造成在url為A頁面,但顯示的是B頁面的內容,造成網址劫持。
比較難以理解的是 last 和 break,讓我們先了解 nginx 運行的11個階段,注意到第四階段:
typedef enum { NGX_HTTP_POST_READ_PHASE = 0, //讀取請求頭 NGX_HTTP_SERVER_REWRITE_PHASE, //執行rewrite NGX_HTTP_FIND_CONFIG_PHASE, //根據uri替換location NGX_HTTP_REWRITE_PHASE, //根據替換結果繼續執行rewrite NGX_HTTP_POST_REWRITE_PHASE, //執行rewrite后處理 NGX_HTTP_PREACCESS_PHASE, //認證預處理 請求限制,連接限制 NGX_HTTP_ACCESS_PHASE, //認證處理 NGX_HTTP_POST_ACCESS_PHASE, //認證后處理, 認證不通過, 丟包 NGX_HTTP_TRY_FILES_PHASE, //嘗試try標簽 NGX_HTTP_CONTENT_PHASE, //內容處理 NGX_HTTP_LOG_PHASE //日志處理 } ngx_http_phases;
所以我們再來理解last與break的區別:
last: 停止當前這個請求,并根據rewrite匹配的規則重新發起一個請求。新請求又從第一階段開始執行…
break:相對last,break并不會重新發起一個請求,只是跳過當前的rewrite階段,并執行本請求后續的執行階段…
通過實例會更加清晰的理解
server { listen 80 default_server; server_name dcshi.com; root www; location /break/ { rewrite ^/break/(.*) /test/$1 break; echo "break page"; } location /last/ { rewrite ^/last/(.*) /test/$1 last; echo "last page"; } location /test/ { echo "test page"; } }
請求:http://dcshi.com/break/*
輸出: break page
分析:正如上面討論所說,break是跳過當前請求的rewrite階段,并繼續執行本請求的其他階段,很明顯,對于/foo 對應的content階段的輸出為 echo “break page”; (content階段,可以簡單理解為產生數據輸出的階段,如返回靜態頁面內容也是在content階段;echo指令也是運行在content階段,一般情況下content階段只能對應一個輸出指令,如同一個location配置兩個echo,最終只會有一個echo指令被執行);當然如果你把/break/里的echo 指令注釋,然后再次訪問/break/xx會報404,這也跟我們預期一樣:雖然/break/xx被重定向到/test/xx,但是break指令不會重新開啟一個新的請求繼續匹配,所以nginx是不會匹配到下面的/test/這個location;在echo指令被注釋的情況下,/break/ 這location里只能執行nginx默認的content指令,即嘗試找/test/xx這個html頁面并輸出起內容,事實上,這個頁面不存在,所以會報404的錯誤。
請求: http://dcshi.com/last/*
輸出: test page
分析: last與break最大的不同是,last會重新發起一個新請求,并重新匹配location,所以對于/last,重新匹配請求以后會匹配到/test/,所以最終對應的content階段的輸出是test page;
解釋完了 last 和 break ,我們再寫一個實例用來說明 rewrite 可以做什么事情。通過rewrite將不帶www的請求統一轉向為www:
server { # ........ server_name www.abc.com ;//只留一個 # ...... } server { server_name abc.com; rewrite ^(.*)$ http://www.abc.com$1 permanent; }
或者是:
server { listen 80; server_name abc.com www.abc.com; if ( $host != "www.abc.com" ) { rewrite ^/(.*) http://www.abc.com/$1 permanent; } location / { root /data/www/www; index index.html index.htm; } }
參考:
http://tool.oschina.net/apidocs/apidoc?api=nginx-zh
https://www.jianshu.com/p/bed000e1830b
http://blog.sina.com.cn/s/blog_4f9fc6e10102ux0w.html
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/39895.html
摘要:既然是從零開始,那么就把作為統一的安裝工具。下面附上安裝方法安裝好之后,就可以開始搭建環境了。環境安裝比較簡單安裝好之后,首先要啟動服務。和一起安裝,我們先去安裝,再做相關配置。成功解析還差一步,就是修改配置文件。 既然是從零開始,那么就把 homebrew 作為統一的安裝工具。如果你不知道 homebrew 是什么東東,移步這里。下面附上 homebrew 安裝方法: /usr/bi...
摘要:既然是從零開始,那么就把作為統一的安裝工具。下面附上安裝方法安裝好之后,就可以開始搭建環境了。環境安裝比較簡單安裝好之后,首先要啟動服務。和一起安裝,我們先去安裝,再做相關配置。成功解析還差一步,就是修改配置文件。 既然是從零開始,那么就把 homebrew 作為統一的安裝工具。如果你不知道 homebrew 是什么東東,移步這里。下面附上 homebrew 安裝方法: /usr/bi...
摘要:在時間段內,日志文件最少使用幾次,該日志文件描述符記入緩存,默認是次。例子中,設置緩存最多緩存個日志文件描述符,內如果緩存中的日志文件描述符至少被被訪問次,才不會被緩存關閉。每隔分鐘檢查緩存中的文件描述符的文件名是否還存在。 前言 Nginx日志對于統計、系統服務排錯很有用。Nginx日志主要分為兩種:access_log(訪問日志)和error_log(錯誤日志)。通過訪問日志我們可...
摘要:買了一個服務器,系統是做了一番基礎設置,在此記錄一下。安裝成功后重啟服務。我采用源碼編譯的方式安裝默認安裝到,可以通過指定安裝目錄。幾個常用的命令啟動停止 買了一個服務器,系統是CentOS7.2 .做了一番基礎設置,在此記錄一下。 更新 yum 源倉庫 yum update 安裝 Git yum 源倉庫里最新版本的 Git 是 1.8.3.1,但是官方最新版本已經到了 2.9.2。想...
閱讀 2511·2021-09-09 09:33
閱讀 2873·2019-08-30 15:56
閱讀 3156·2019-08-30 14:21
閱讀 905·2019-08-30 13:01
閱讀 868·2019-08-26 18:27
閱讀 3591·2019-08-26 13:47
閱讀 3458·2019-08-26 10:26
閱讀 1593·2019-08-23 18:38