Nginx
本文裡面介紹了 Nginx的安裝,代理,負載均衡,location的正則配置,動靜分離,快取,壓縮,防盜鏈,跨域處理
1. 定義:
Nginx 是一個HTTP和反向代理伺服器,一個郵件代理伺服器和一個通用的TCP/UDP代理伺服器。
2. 簡介
-
Nginx 是一個高效能的 Web 和反向代理伺服器, 它具有有很多非常優越的特性:
-
作為 Web 伺服器:相比 Apache,Nginx 使用更少的資源,支援更多的併發連線,體現更高的效率,這點使 Nginx 尤其受到虛擬主機提供商的歡迎。能夠支援高達 50,000 個併發連線數的響應,感謝 Nginx 為我們選擇了 epoll and kqueue 作為開發模型.
-
作為負載均衡伺服器:Nginx 既可以在內部直接支援 Rails 和 PHP,也可以支援作為 HTTP代理伺服器對外進行服務。Nginx 用 C 編寫, 不論是系統資源開銷還是 CPU 使用效率都比 Perlbal 要好的多。
-
作為郵件代理伺服器: Nginx 同時也是一個非常優秀的郵件代理伺服器(最早開發這個產品的目的之一也是作為郵件代理伺服器),Last.fm 描述了成功並且美妙的使用經驗。
-
Nginx 安裝非常的簡單,配置檔案 非常簡潔(還能夠支援perl語法),Bugs非常少的伺服器:Nginx啟動特別容易,並且幾乎可以做到7*24不間斷執行,即使執行數個月也不需要重新啟動。你還能夠在不間斷服務的情況下進行軟體版本的升級。
3. 安裝
Windos安裝:
-
下載nginx nginx.org/download/ng…
-
雙擊啟動nginx程式
Linux安裝:
在linux下面存在兩種安裝方式:
- 編譯安裝
- yum安裝
Yum安裝 【centOs7才有Yum】:
- 如果沒有安裝 Nginx 的源需要安裝一下Nginx的源
rpm -Uvh http://nginx.org/packages/centos/7/noarch/RPMS/nginx-release-centos-7-0.el7.ngx.noarch.rpm
複製程式碼
[1] Yum 安裝 Nginx
yum install nginx
複製程式碼
[2] 命令 Nginx 啟動 Nginx服務
nginx
複製程式碼
[3] nginx的路徑如下
(1) Nginx配置路徑:/etc/nginx/
(2) PID目錄:/var/run/nginx.pid
(3) 錯誤日誌:/var/log/nginx/error.log
(4) 訪問日誌:/var/log/nginx/access.log
(5) 預設站點目錄:/usr/share/nginx/html
複製程式碼
編譯安裝:
- 下載nginx
wget http://nginx.org/download/nginx-1.15.12.tar.gz
複製程式碼
- 安裝需要編譯的外掛
Gcc:yum install gcc c++ (用於編譯c、c++程式碼)
Pcre:yum install -y pcre pcre-devel (用c語言編寫的正規表示式函式庫))
Zlib:yum install -y zlib zlib-devel (用於資料壓縮的函式庫))
OpenSSL:yum install -y openssl openssl-devel (安全套接字層密碼庫))
yum install -y pcre pcre-devel
yum install -y zlib zlib-devel
yum install -y openssl openssl-devel
複製程式碼
- 編譯Nginx
tar -zxvf nginx-1.15.tar.gz
cd nginx-1.15
./configure
make
make install
複製程式碼
- 啟動nginx
cd /usr/local/nginx/
cd sbin/
./nginx
複製程式碼
3. 代理
正向代理:正向代理代理的是使用者
反向代理:方向代理代理的是伺服器
4. 準備
我們要演示Nginx的相關配置需要3臺伺服器,裡面用Tomcat。為了我們區分我們在每個Tomcat裡面的index.jsp裡面寫入的本機的Ip。啟動Tomcat,出現如下效果。
我們隨機選擇其中一臺,修改裡面的 nginx.conf
# http://10.18.3.197/ 代理
server {
listen 80 default_server;
listen [::]:80 default_server;
server_name _;
root /usr/share/nginx/html;
# Load configuration files for the default server block.
include /etc/nginx/default.d/*.conf;
location / {
proxy_pass http://127.0.0.1:8080;
}
error_page 404 /404.html;
location = /40x.html {
}
error_page 500 502 503 504 /50x.html;
location = /50x.html {
}
}
複製程式碼
那麼代理了本機8080埠的資料
接下來我們使用windos的本機的Host劫持
進入 C:\Windows\System32\drivers\etc 這個檔案
修改 hosts 檔案
在裡面新增 10.18.3.197 test.com
複製程式碼
我們瀏覽器訪問如圖:
我們準備好了環境和相關配置那麼我們接下來看Nginx的一些配置。
5. location配置
location = /uri 精準匹配
location ^~ /uri 字首匹配
location ~ /uri
location / 通用匹配
舉個例子:
1 location = /
2 location = /index
3 location ^~ /article/
4 location ^~ /article/files/
5 location ~ .(gif|png|js|css)$
6 location /
http://10.18.3.197/
http://10.18.3.197/index ->2
http://10.18.3.197/article/files/1.txt ->4
http://10.18.3.197/mic.png ->5
6. Nginx的外掛的使用
# 使用編譯安裝的時候外掛的安裝按時
./configure --prefix=/安裝目錄 --add-module = /第三方模組的目錄 <br/>
./configure --prefix=/data/program/nginx --with-http_stub_status_module --withhttp_random_index_module
cp objs/nginx $nginx_home/sbin/nginx
複製程式碼
舉個例子
安裝 http_stub_status_module
# 檢視nginx的狀態
location /status {
stub_status;
}
複製程式碼
Active: connections:當前狀態,活動狀態的連線數
accepts:統計總值,已經接受的客戶端請求的總數
handled:統計總值,已經處理完成的客戶端請求的總數
requests:統計總值,客戶端發來的總的請求數
Reading:當前狀態,正在讀取客戶端請求報文首部的連線的連線數
Writing:當前狀態,正在向客戶端傳送響應報文過程中的連線數
Waiting:當前狀態,正在等待客戶端發出請求的空閒連線數
7.Nginx負載均衡
一、 輪詢
每個請求按時間順序逐一分配到不同的後端伺服器,如果後端伺服器down掉,能自動剔除。
# 負載均衡預設的輪詢演算法
upstream webserver {
server 10.18.14.59:8080;
server 10.18.14.109:8080;
server 10.18.3.197:8080;
}
server {
...
location / {
# proxy_pass http://127.0.0.1:8080;
proxy_pass http://webserver;
}
}
...
}
複製程式碼
每一次的重新整理瀏覽器裡面的地址,得到都是一個新的伺服器的IP,進行輪訓。
如果我們關閉掉其中的一條伺服器,然後去訪問我們發現,當機的那臺伺服器不會被訪問。如果我們再次重啟那臺當機的伺服器,重新整理瀏覽器的IP地址我們發現又可以負載均衡到那臺伺服器上面了。
二、 輪詢加權
# 負載均輪詢加權演算法
upstream webserver {
server 10.18.14.59:8080 weight=2;
server 10.18.14.109:8080 weight=3;
server 10.18.3.197:8080 weight=5;
}
複製程式碼
每臺伺服器處理的請求數量,跟權重成正比。也就是權重越大,處理的請求數量越多。
三、 ip_hash
如果客戶已經訪問了某個伺服器,當使用者再次訪問時,會將該請求通過雜湊演算法,自動定位到該伺服器。每個請求按訪問ip的hash結果分配,這樣每個訪客固定訪問一個後端伺服器。我們發我們每一次的重新整理並沒有分配到其他機器,而是一直在同一臺機器上,如果當機後重新分配後,不在改變。
# 負載均衡ip_hash演算法
upstream webserver {
ip_hash; #保證每個訪客固定訪問一個後端伺服器
server 10.18.14.59:8080;
server 10.18.14.109:8080;
server 10.18.3.197:8080;
}
複製程式碼
四、least_conn 最小連線數
把請求轉發給連線數較少的後端伺服器。輪詢演算法是把請求平均的轉發給各個後端,使它們的負載大致相同;但是,有些請求佔用的時間很長,會導致其所在的後端負載較高。這種情況下,least_conn這種方式就可以達到更好的負載均衡效果。
# 負載均衡最小連線數演算法
upstream webserver {
least_conn; #把請求轉發給連線數較少的後端伺服器
server 10.18.14.59:8080;
server 10.18.14.109:8080;
server 10.18.3.197:8080;
}
複製程式碼
此負載均衡策略適合請求處理時間長短不一造成伺服器過載的情況。
五、fair 響應時間最短
按照伺服器端的響應時間來分配請求,響應時間短的優先分配。
# 負載均衡響應時間最短演算法
upstream webserver {
server 10.18.14.59:8080;
server 10.18.14.109:8080;
server 10.18.3.197:8080;
fair; #實現響應時間短的優先分配
}
複製程式碼
六、url_hash
按訪問url的hash結果來分配請求,使每個url定向到同一個後端伺服器,要配合快取命中來使用。同一個資源多次請求,可能會到達不同的伺服器上,導致不必要的多次下載,快取命中率不高,以及一些資源時間的浪費。而使用url_hash,可以使得同一個url(也就是同一個資源請求)會到達同一臺伺服器,一旦快取住了資源,再此收到請求,就可以從快取中讀取。
# 負載均衡url_hash演算法
upstream webserver {
hash $request_uri; #實現每個url定向到同一個後端伺服器
server 10.18.14.59:8080;
server 10.18.14.109:8080;
server 10.18.3.197:8080;
}
複製程式碼
8、相關的配置資訊
- proxy_next_upstream
proxy_next_upstream
語法:proxy_next_upstream [error | timeout | invalid_header | http_500 | http_502 | http_503 | http_504 | http_404 | off ];
預設:proxy_next_upstream error timeout;
配置塊:http、server、location
這個配置表示當向一臺上有伺服器轉發請求出現錯誤的時候,繼續換一臺上後伺服器來處理這個請求。 預設情況下,上游伺服器一旦開始傳送響應資料,Nginx反向代理伺服器會立刻把應答包轉發給客戶端。因此,一 旦Nginx開始向客戶端傳送響應包,如果中途出現錯誤也不允許切換到下一個上有伺服器繼續處理的。這樣做的目 的是保證客戶端只收到來自同一個上游伺服器的應答。
- proxy_connect_timeout
proxy_connect_timeout
語法: proxy_connect_timeout time;
預設: proxy_connect_timeout 60s;
配置塊: http, server, location
用於設定nginx與upstream server的連線超時時間,比如我們直接在location中設定proxy_connect_timeout 1ms, 1ms很短,如果無法在指定時間建立連線,就會報錯。
- proxy_send_timeout
向後端寫資料的超時時間,兩次寫操作的時間間隔如果大於這個值,也就是過了指定時間後端還沒有收到資料,連 接會被關閉
- proxy_read_timeout
從後端讀取資料的超時時間,兩次讀取操作的時間間隔如果大於這個值,那麼nginx和後端的連結會被關閉,如果 一個請求的處理時間比較長,可以把這個值設定得大一些
-
proxy_upstream_fail
-
proxy_upstream_fail_timeout
設定了某一個upstream後端失敗了指定次數(max_fails)後,在fail_timeout時間內不再去請求它,預設為10秒 語法 server address [fail_timeout=30s]
upstream backend { #伺服器叢集名字
server 192.168.218.129:8080 weight=1 max_fails=2 fail_timeout=600s;
server 192.168.218.131:8080 weight=1 max_fails=2 fail_timeout=600s;
}
複製程式碼
9.處理跨域問題
什麼叫跨域呢?如果兩個節點的協議、域名、埠、子域名不同,那麼進行的操作都是跨域的,瀏覽器為了安全問 題都是限制跨域訪問,所以跨域其實是瀏覽器本身的限制。
location / {
proxy_pass http://webserver;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_next_upstream error timeout http_500 http_503;
proxy_connect_timeout 60s;
proxy_send_timeout 60s;
proxy_read_timeout 60s;
add_header 'Access-Control-Allow-Origin' '*'; // #允許來自所有的訪問地址
add_header 'Access-Control-Allow-Methods' 'GET,PUT,POST,DELETE,OPTIONS'; //支援的請求方式
add_header 'Access-Control-Allow-Header' 'Content-Type,*'; //支援的媒體型別
}
複製程式碼
10.動靜分離
必須依賴伺服器生存的我們稱為動。不需要依賴容器的比如css/js或者圖片等,這類就叫靜。
靜態資源型別
types {
text/html html htm shtml;
text/css css;
text/xml xml;
image/gif gif;
image/jpeg jpeg jpg;
application/javascript js;
application/atom+xml atom;
application/rss+xml rss;
text/mathml mml;
text/plain txt;
text/vnd.sun.j2me.app-descriptor jad;
text/vnd.wap.wml wml;
text/x-component htc;
image/png png;
image/svg+xml svg svgz;
image/tiff tif tiff;
image/vnd.wap.wbmp wbmp;
image/webp webp;
image/x-icon ico;
image/x-jng jng;
image/x-ms-bmp bmp;
application/font-woff woff;
application/java-archive jar war ear;
application/json json;
application/mac-binhex40 hqx;
application/msword doc;
application/pdf pdf;
application/postscript ps eps ai;
application/rtf rtf;
application/vnd.apple.mpegurl m3u8;
application/vnd.google-earth.kml+xml kml;
application/vnd.google-earth.kmz kmz;
application/vnd.ms-excel xls;
application/vnd.ms-fontobject eot;
application/vnd.ms-powerpoint ppt;
application/vnd.oasis.opendocument.graphics odg;
application/vnd.oasis.opendocument.presentation odp;
application/vnd.oasis.opendocument.spreadsheet ods;
application/vnd.oasis.opendocument.text odt;
application/vnd.openxmlformats-officedocument.presentationml.presentation
pptx;
application/vnd.openxmlformats-officedocument.spreadsheetml.sheet
xlsx;
application/vnd.openxmlformats-officedocument.wordprocessingml.document
docx;
application/vnd.wap.wmlc wmlc;
application/x-7z-compressed 7z;
application/x-cocoa cco;
application/x-java-archive-diff jardiff;
application/x-java-jnlp-file jnlp;
application/x-makeself run;
application/x-perl pl pm;
application/x-pilot prc pdb;
application/x-rar-compressed rar;
application/x-redhat-package-manager rpm;
application/x-sea sea;
application/x-shockwave-flash swf;
application/x-stuffit sit;
application/x-tcl tcl tk;
application/x-x509-ca-cert der pem crt;
application/x-xpinstall xpi;
application/xhtml+xml xhtml;
application/xspf+xml xspf;
application/zip zip;
application/octet-stream bin exe dll;
application/octet-stream deb;
application/octet-stream dmg;
application/octet-stream iso img;
application/octet-stream msi msp msm;
audio/midi mid midi kar;
audio/mpeg mp3;
audio/ogg ogg;
audio/x-m4a m4a;
audio/x-realaudio ra;
video/3gpp 3gpp 3gp;
video/mp2t ts;
video/mp4 mp4;
video/mpeg mpeg mpg;
video/quicktime mov;
video/webm webm;
video/x-flv flv;
video/x-m4v m4v;
video/x-mng mng;
video/x-ms-asf asx asf;
video/x-ms-wmv wmv;
video/x-msvideo avi;
}
複製程式碼
在Nginx的conf目錄下,有一個mime.types
檔案使用者訪問一個網站,然後從伺服器端獲取相應的資源通過瀏覽器進行解析渲染最後展示給使用者,而服務端可以返回各種型別的內容,比如xml、jpg、png、gif、flash、MP4、html、css等等,那麼瀏覽器就是根據mime-type來決定用什麼形式來展示的伺服器返回的資源給到瀏覽器時,會把媒體型別告知瀏覽器,這個告知的標識就是Content-Type,比如ContentType:text/html。
location ~ .*\.(js|css|png|svg|ico|jpg) {
root /.(路徑)./static-resource; # 指定訪問的目錄
}
複製程式碼
舉個例子:
我們設定攔截靜態資源,然後刪除本機tomcat裡面的靜態資源,得到如下:
將我們刪除的tomcat靜態資源放入對應的資料夾內
動靜分離的好處
第一個,Nginx本身就是一個高效能的靜態web伺服器;
第二個,其實靜態檔案有一個特點就是基本上變化不大,所以動靜分離以後我們可以對靜態檔案進行快取、或者壓 縮提高網站效能。現在比較流行前後端分離,這樣可以大大減輕服務端的壓力
12.快取配置
當一個客戶端請求web伺服器, 請求的內容可以從以下幾個地方獲取:伺服器、瀏覽器快取中或快取伺服器中。這取決於伺服器端輸出的頁面資訊瀏覽器快取將檔案儲存在客戶端,好的快取策略可以減少對網路頻寬的佔用,可以提高訪問速度,提高使用者的體驗,還可以減輕伺服器的負擔nginx快取配置
Nginx快取配置
Nginx可以通過expires設定快取,比如我們可以針對圖片做快取,因為圖片這類資訊基本上不會改變。 在location中設定expires
格式: expires 30s|m|h|d
location ~ .*\.(jpg|jpeg|gif|bmp|png|js|css|ico) {
root static;
expires 1d; # 設定過期時間為1天
}
複製程式碼
13.壓縮
我們一個網站一定會包含很多的靜態檔案,比如圖片、指令碼、樣式等等,而這些css/js可能本身會比較大,那麼在 網路傳輸的時候就會比較慢,從而導致網站的渲染速度。因此Nginx中提供了一種Gzip的壓縮優化手段,可以對後 端的檔案進行壓縮傳輸,壓縮以後的好處在於能夠降低檔案的大小來提高傳輸效率。
配置資訊
Gzip on|off 是否開啟gzip壓縮
Gzip_buffers 4 16k #設定gzip申請記憶體的大小,作用是按指定大小的倍數申請記憶體空間。4 16k代表按照原始資料 大小以16k為單位的4倍申請記憶體。
Gzip_comp_level[1-9] 壓縮級別, 級別越高,壓縮越小,但是會佔用CPU資源
Gzip_disable #正則匹配UA 表示什麼樣的瀏覽器不進行gzip
Gzip_min_length #開始壓縮的最小長度(小於多少就不做壓縮),可以指定單位,比如 1k
Gzip_http_version 1.0|1.1 表示開始壓縮的http協議版本
Gzip_proxied (nginx 做前端代理時啟用該選項,表示無論後端伺服器的headers頭返回什麼資訊,都無條件啟用 壓縮)
Gzip_type text/pliain,application/xml 對那些型別的檔案做壓縮 (conf/mime.conf)
Gzip_vary on|off 是否傳輸gzip壓縮標識; 啟用應答頭"Vary: Accept-Encoding";給代理伺服器用的,有的瀏覽器支 持壓縮,有的不支援,所以避免浪費不支援的也壓縮,所以根據客戶端的HTTP頭來判斷,是否需要壓縮
http {
gzip on;
gzip_min_length 5k;
gzip_comp_level 3;
gzip_types application/javascript image/jpeg image/svg+xml;
gzip_buffers 4 32k;
gzip_vary on;
}
複製程式碼
14.防盜鏈
http 協議中,如果從一個網頁跳到另一個網頁,http 頭欄位裡面會帶個 Referer。圖片伺服器通過檢測 Referer 是否來自規定域名,來進行防盜鏈。
語法: valid_referers none | blocked | server_names | string ...;
預設值: —
上下文: server, location
“Referer”請求頭為指定值時,內嵌變數$invalid_referer被設定為空字串,否則這個變數會被置成“1”。查詢匹配 時不區分大小寫,其中none表示缺少referer請求頭、blocked表示請求頭存在,但是它的值被防火牆或者代理服務 器刪除、server_names表示referer請求頭包含指定的虛擬主機名
配置如下
server {
...
server_name test.com;
...
location ~ .*\.(gif|jpg|ico|png|css|svg|js) {
valid_referers none blocked test.com 10.18.3.197;
if ($invalid_referer) {
return 404;
}
root static;
}
...
}
複製程式碼
需要注意的是偽造一個有效的“Referer”請求頭是相當容易的,因此這個模組的預期目的不在於徹底地阻止這些非法請求,而 是為了阻止由正常瀏覽器發出的大規模此類請求。還有一點需要注意,即使正常瀏覽器傳送的合法請求,也可能沒 有“Referer”請求頭。
還有跟多的防盜鏈的配置和破解我在就不描述了,應為在對頁面也就是前端來說,沒有絕對的安全。
下面是關於nginx的防盜鏈的文章和防盜鏈的防禦和破解。 www.cnblogs.com/limeng951/p…
www.cnblogs.com/saysmy/p/86…
這個裡面講了如何禁止使用F12檢視原始碼,以及右鍵檢視元素
www.3lian.com/edu/2013/10…
但是這些都不能反正檢視原始碼,如果我用之前就開啟F12模式在進入你的網站你如何防護呢?所以對於前端來說沒有絕對的安全和保密。