《適用於開發人員的Nginx秘籍》 蟲蟲搜奇優質科技領域創作者要問目前哪個Web服務器最流行,可能大家都會說是Nginx。這個老毛子開發的神器憑借高性能了、友好的配置、優秀的模塊機制,反向代理支持迅速占領市場並走上Web服務器市場的No1. 本文我們就來談談對於開發人員來說Nginx的一些妙用方法。 從這個簡單的配置,我們可以開始構建必要的複雜性。主動/被動代理配置如果服務需要以一台服務器為主的主動/被動配置 對於請求處理,將一個後端服務器做備份,配置方法如下:upstream backend {server job:10000;server backup:10000 backup;}Backup選項指示,表示nginx將使用該服務器為備用服務器,只有當主服務器(job:10000)不可用時候,才會代理到backup:10000。默認情況下,服務器在1次連接錯誤或超時後標記為不可用。但是該閾值可以通過max_fails來配置:upstream backend {# 主服務器失敗嘗試3次server job:10000 max_fails=3;# 備用服務器嘗試失敗次數10server backup:10000 backup max_fails=10;}除了連接錯誤和超時,還可以使用HTTP 狀態碼,比如500,502等來定義不可用狀態。該配置,由proxy_next_upstream語句定義。upstream backend {server job:10000;server backup:10000 backup;}server {server_name proxy;listen 8000;# 在連接錯誤,超時或者http 429(請求超出)的時候時候,跳轉到下一個pstream。proxy_next_upstream error timeout http_429;location / {proxy_pass http://backend;}}代理K8s服務如果要代理K8s集群服務,由於其自帶負載均衡配置中應該設置max_fails=0,以免踢掉正常的服務器:upstream backend {server cck8s.svc max_fails=0;}這樣nginx就不會將 K8s服務標記為不可用。即不會去嘗試做被動健康檢查,直接利用的K8s集群的主動健康檢查。靈活的路由 map有時需要根據某些HTTP標頭值路由請求。比如查詢範圍、cookie值或、主機名或者他們的任意組合。這是Nginx最強大的地方,其他同類的代理基本上都做不到這一點。Nginx請求路由的關鍵是ngx_http_map_module。該模塊允許從組合中定義變量帶有正則表達式的變量。假設微服務架構中有3個後端服務來處理不同類型的數據:返回剛剛收集的最新數據的實時數據服務。返回舊數據的歷史數據服務。返回預先計算的數據的聚合數據服務。這些服務通過相同的接口提供用戶服務,接口形式如下<date>.cc.api/?report=<report>現在有幾個用戶用例:2021-04-01.cc.api/?report=list_records 應該提供歷史數據服務。cc.api/?report=list_records 應該提供實時數據服務。cc.api/?report=counters提供聚合數據服務。2018-11-01.cc.api/?report=counters 提供歷史聚合數據服務。如果自己在程序中自己寫路由則非常複雜,而用Nginx可以幫你通過很少配置就搞定:首先,定義3個後端服務器:upstream live {server live1:8000;server live2:8000;server live3:8000;}upstream hist {server hist1:9999;server hist2:9999;}upstream agg {server agg1:7100;server agg2:7100;server agg3:7100;}接下來,定義將偵聽所有請求並以某種方式路由提供服務:server {server_name *.cc.api "";listen 80;location / {proxy_pass http://???;}}問題是我們應該寫什麼proxy_pass指示?由於nginx配置是聲明性的,可以編寫 proxy_pass http://$destination/並使用map構建目標變量。示例服務中,根據report請求變量和日期子域名,提取到變量中的內容為:map $host $date {"~^((?<subdomain>d{4}-d{2}-d{2}).)?cc.api$" $subdomain;default "";}Map會通過正則解析$host變量,並將解析結果設置$date。此處主要使用了有2條map規則 :主要的規則是正則表達式,另一個是後備表示為default關鍵詞。正則表示式子,我們不在詳細介紹,如果有興趣可以搜索蟲蟲以前的文章。此處規則為^開頭,提取時間子域名:d{4}-d{2}-d{2}解析日期格式 2021-06-28。?<subdomain>被稱為捕獲組,它只是為匹配的部分命名正則表達式。然後在映射規則的右側使用捕獲組來分配。$date多變,而且子域是可選的,因此需要 用圓括號括起來(子域分隔符)並在整個組前添加?。要提取report,無需使用map,nginx的arg_<param>查詢參數的是預定義變量。 可以直接用$arg_report。好的,有了日期report告。接著構建 $destination變量,用另一個map,訣竅是在後面map中可以利用上面的變量(包括自定義的)創建新變量的變量組合:map "$arg_report:$date" $destination {"~counters:.*" agg;"~.*:.+" hist;default live;}這裏的組合是一個字符串,其中2個變量用冒號連接。冒號是個人選擇,用於方便。實際上可以使用任何符號,只要確保正則表達式是明確的。在map,有3個規則。首先是設置$destination到gg時report查詢參數是 counters。二是設置 $destination到 hist時,$date變量不為空。當沒有其他匹配時設置的默認值是設置$destination至 live。map中的正則表達式按順序進行評估。注意 $destinationvalue 是代理後端的名稱。完整的配置如下:events {}http {upstream live {server live1:8000;server live2:8000;server live3:8000;}upstream hist {server hist1:9999;server hist2:9999;}upstream agg {server agg1:7100;server agg2:7100;server agg3:7100;}map $host $date {"~^((?<subdomain>d{4}-d{2}-d{2}).)?cc.api$" $subdomain;default "";}map "$arg_report:$date" $destination {"~counters:.*" agg;"~.*:.+" hist;default live;}server {server_name *.cc.api "";listen 80;location / {proxy_pass http://$destination/;}}}轉發請求給Consul服務如果使用Consul進行服務發現,則可以通過以下方式訪DNS。 簡單的curl myapp.service.consul。非常方便,但沒有人知道如何解析名稱 .consul zone。無論如何,要通過 Consul DNS 在 nginx 中路由請求很一件。nginx有一個 resolver模塊nginx 中用於使用自定義 DNS 服務器的指令(注意就是最近爆嚴重漏洞的那個高危寫入漏洞的CVE-2021-23017的模塊,記得升級哦)。以下下面是配置Nginx轉發DNS請求給Consul配置:server {server_name *.cc.api "";listen 80;# 解析使用Consul DNS. 遞歸請求到114和谷歌DNS.resolver 10.0.0.1:8600 10.0.0.2:8600 10.0.0.3:8600 114.114.114.114 8.8.8.8location /v1/api {proxy_pass http://prod.cc.api.consul/;}location /v1/rpc {proxy_pass http://prod.rpc.service.consul/;}}結論Nginx 是一個非常通用的工具。 它有豐富的配置語言為開發人員提供不錯的功能。比如具有配置故障轉移的主動/被動負載平衡、靈活的請求路由與Consul DNS 輕松集成等。雖然有些配置比較醜,甚至使用了可怕的正則,但是這也許就是他的魅力所在吧。 《適用於開發人員的Nginx秘籍》完,請繼續朗讀精采文章。 喜歡 小編的世界 e4to.com,請記得按讚、收藏及分享!
音調
速度
音量
語言
適用於開發人員的Nginx秘籍
精確朗讀模式適合大多數瀏覽器,也相容於桌上型與行動裝置。
不過,使用Chorme瀏覽器仍存在一些問題,不建議使用Chorme瀏覽器進行精確朗讀。