傳統上基於進程或線程模型架構的web服務通過每進程或每線程處理並發連接請求,這勢必會在網絡和I/O操作時產生阻塞,其另一個必然結果則是對內存或CPU的利用率低下。生成一個新的進程/線程需要事先備好其運行時環境,這包括為其分配堆內存和棧內存,以及為其創建新的執行上下文等。這些操作都需要占用CPU,而且過多的進程/線程還會帶來線程抖動或頻繁的上下文切換,系統性能也會由此進一步下降。
在設計的最初階段,nginx的主要着眼點就是其高性能以及對物理計算資源的高密度利用,因此其采用了不同的架構模型。受啟發於多種操作系統設計中基於“事件”的高級處理機制,nginx采用了模塊化、事件驅動、異步、單線程及非阻塞的架構,並大量采用了多路復用及事件通知機制。在nginx中,連接請求由為數不多的幾個僅包含一個線程的進程worker以高效的回環(run-loop)機制進行處理,而每個worker可以並行處理數千個的並發連接及請求。
如果負載以CPU密集型應用為主,如SSL或壓縮應用,則worker數應與CPU數相同;如果負載以IO密集型為主,如響應大量內容給客戶端,則worker數應該為CPU個數的1.5或2倍。
Nginx會按需同時運行多個進程:一個主進程(master)和幾個工作進程(worker),配置了緩存時還會有緩存加載器進程(cache loader)和緩存管理器進程(cache manager)等。所有進程均是僅含有一個線程,並主要通過“共享內存”的機制實現進程間通信。主進程以root用戶身份運行,而worker、cache loader和cache manager均應以非特權用戶身份運行。
1.主進程(Master Process)
主要完成如下工作:
- 讀取並驗正配置信息;
- 創建、綁定及關閉套接字;
- 啟動、終止及維護worker進程的個數;
- 無須中止服務而重新配置工作特性;
- 控制非中斷式程序升級,啟用新的二進制程序並在需要時回滾至老版本;
- 重新打開日志文件,實現日志滾動;
- 編譯嵌入式perl腳本;
2.工作進程(Worker Process)
- 接收、傳入並處理來自客戶端的連接;
- 提供反向代理及過濾功能;
- nginx任何能完成的其它任務;
3.緩存索引重建及進程管理(Cache Loader & Cache Manager)
Cache模塊,主要由緩存索引重建(Cache Loader)和緩存索引管理(Cache Manager)兩類進程完成工作。緩存索引重建進程是在Nginx服務啟動一段時間之后(默認是1分鍾)由主進程生成,在緩存元數據重建完成后就自動退出;緩存索引管理進程一般存在於主進程的整個生命周期,負責對緩存索引進行管理。
cache loader進程主要完成的任務包括:
- 檢查緩存存儲中的緩存對象;
- 使用緩存元數據建立內存數據庫;
cache manager進程的主要任務:
- 緩存的失效及過期檢驗;