天天看點

nginx的負載均衡那點事

前言:

随着網際網路資訊的爆炸性增長,負載均衡(load balance)已經不再是一個很陌生的話題,顧名思義,負載均衡即是将負載分攤到不同的服務單元,既保證服務的可用性,又保證響應足夠快,給使用者很好的體驗。快速增長的通路量和資料流量催生了各式各樣的負載均衡産品,很多專業的負載均衡硬體提供了很好的功能,但卻價格不菲,這使得負載均衡軟體大受歡迎,nginx就是其中的一個。

nginx的負載均衡那點事

nginx第一個公開版本釋出于2004年,2011年釋出了1.0版本。它的特點是穩定性高、功能強大、資源消耗低,從其目前的市場占有而言,nginx大有與apache搶市場的勢頭。其中不得不提到的一個特性就是其負載均衡功能,這也成了很多公司選擇它的主要原因。本文将從源碼的角度介紹nginx的内置負載均衡政策和擴充負載均衡政策,以實際的工業生産為案例,對比各負載均衡政策,為nginx使用者提供參考。

本節就聊聊采用Nginx負載均衡之後碰到的問題:

nginx的負載均衡那點事
  • Session問題
  • 檔案上傳下載下傳

通常解決伺服器負載問題,都會通過多伺服器分載來解決。常見的解決方案有:

nginx的負載均衡那點事
  • 網站入口通過分站連結負載(天空軟體站,華軍軟體園等)
  • DNS輪詢
  • F5實體裝置
  • Nginx等輕量級架構

那我們看看Nginx是如何實作負載均衡的,Nginx的upstream目前支援以下幾種方式的配置設定

1、輪詢(預設)

每個請求按時間順序逐一配置設定到不同的後端伺服器,如果後端伺服器down掉,能自動剔除。

2、weight

指定輪詢幾率,weight和通路比率成正比,用于後端伺服器性能不均的情況。

2、ip_hash

每個請求按通路ip的hash結果配置設定,這樣每個訪客固定通路一個後端伺服器,可以解決session的問題。

3、fair(第三方)

按後端伺服器的響應時間來配置設定請求,響應時間短的優先配置設定。

4、url_hash(第三方)

按通路url的hash結果來配置設定請求,使每個url定向到同一個後端伺服器,後端伺服器為緩存時比較有效。

Upstream配置如何實作負載   

View Code

當有請求到www.test1.com/www.test2.com 時請求會被分發到對應的upstream設定的伺服器清單上。test2的每一次請求分發的伺服器都是随機的,就是第一種情況列舉的。而test1剛是根據來通路ip的hashid來分發到指定的伺服器,也就是說該IP的請求都是轉到這個指定的伺服器上。

根據伺服器的本身的性能差别及職能,可以設定不同的參數控制。

down 表示負載過重或者不參與負載

weight 權重過大代表承擔的負載就越大

backup 其它伺服器時或down時才會請求backup伺服器

max_fails 失敗超過指定次數會暫停或請求轉往其它伺服器

fail_timeout 失敗超過指定次數後暫停時間

以上就Nginx的負載均衡的簡單配置。那繼續我們的本節讨論内容:

一、Session問題

當我們确定一系列負載的伺服器後,那我們的WEB站點會分布到這些伺服器上。這個時候如果采用Test2 每一次請求随機通路任何一台伺服器上,這樣導緻你通路A伺服器後,下一次請求又突然轉到B伺服器上。這個時候與A伺服器建立的Session,傳到B站點伺服器肯定是無法正常響應的。我們看一下常用的解決方案:

  • Session或憑據緩存到獨立的伺服器
  • Session或憑據儲存資料庫中
  • nginx ip_hash 保持同一IP的請求都是指定到固定的一台伺服器

第一種緩存的方式比較理想,緩存的效率也比較高。但是每一台請求伺服器都去通路Session會話伺服器,那不是加載重了這台Session伺服器的負擔嗎?

第二種儲存到資料庫中,除了要控制Session的有效期,同時加重了資料庫的負擔,是以最終的轉變為SQL Server 負載均衡,涉及讀,寫,過期,同步。

第三種通過nginx ip_hash負載保持對同一伺服器的會話,這種看起來最友善,最輕量。

正常情況下架構簡單的話, ip_hash可以解決Session問題,但是我們來看看下面這種情況

nginx的負載均衡那點事

這個時候ip_hash 收到的請求都是來自固定IP代理的請求,如果代理IP的負載過高就會導緻ip_hash對應的伺服器負載壓力過大,這樣ip_hash就失去了負載均衡的作用了。

如果緩存可以實作同步共享的話,我們可以通過多session伺服器來解決單一負載過重的問題。那Memcached是否可以做Session緩存伺服器呢?MemcachedProvider提供了Session的功能,即将Session儲存到資料庫中。那為什麼不直接儲存到資料庫中,而要通過Memcached儲存到資料庫中呢?很簡單,如果直接儲存到資料庫中,每一次請求Session有效性都要回資料庫驗證一下。其次,即使我們為資料庫建立一層緩存,那這個緩存也無法實作分布式共享,還是針對同一台緩存伺服器負載過重。網上也看到有用Memcached實作Session緩存的成功案例,當然資料庫方式實作的還是比較常用的,比如開源Disuz.net論壇。緩存實作的小範圍分布式也是比較常用的,比如單點登入也是一種特殊情況。

二、檔案上傳下載下傳

如果實作了負載均衡,除了Session問題,我們還會碰到檔案的上傳下載下傳問題。檔案不可能上傳不同的伺服器上,這樣會導緻下載下傳不到對應檔案的問題。我們看一下下面的方案

  • 獨立檔案伺服器 
  • 檔案壓縮資料庫

兩種方案都是常用的,我們來說一下檔案壓縮資料庫,以前的方式都是将檔案二進制壓縮至關系型資料庫,而現在NOSQL的流行,加上MongoDB處理檔案又比較友善,是以檔案壓庫又多了一種選擇。畢竟檔案伺服器的效率和管理以及安全都不及資料庫。

随便聊聊這點事,其實也就是一些應用的趨勢和多一種解決方案的實作。