nginx模塊描述,模塊分類,處理流程

一,模塊概述html


nginx將各功能模塊組織成一條鏈,當有請求到達的時候,請求依次通過這條鏈上的部分或者所有模塊,進行處理。每一個模塊實現特定的功能。例如,實現對請求解壓縮的模塊,實現SSI的模塊,實現與上游服務器進行通信的模塊,實現與FastCGI服務進行通信的模塊。nginx

有兩個模塊比較特殊,他們居於nginx core和各功能模塊的中間。這兩個模塊就是http模塊和mail模塊。這2個模塊在nginx core之上實現了另一層抽象,處理與HTTP協議和email相關協議(SMTP/POP3/IMAP)有關的事件,而且確保這些事件能被以正確的順序調用其餘的一些功能模塊。算法

目前HTTP協議是被實如今http模塊中的,可是有可能未來被剝離到一個單獨的模塊中,以擴展nginx支持SPDY協議。後端

二,模塊的分類服務器


nginx的模塊根據其功能基本上能夠分爲如下幾種類型:併發

event module: 搭建了獨立於操做系統的事件處理機制的框架,及提供了各具體事件的處理。包括ngx_events_module, ngx_event_core_module和ngx_epoll_module等。nginx具體使用何種事件處理模塊,這依賴於具體的操做系統和編譯選項。負載均衡

phase handler: 此類型的模塊也被直接稱爲handler模塊。主要負責處理客戶端請求併產生待響應內容,好比ngx_http_static_module模塊,負責客戶端的靜態頁面請求處理並將對應的磁盤文件準備爲響應內容輸出。框架

output filter: 也稱爲filter模塊,主要是負責對輸出的內容進行處理,能夠對輸出進行修改。例如,能夠實現對輸出的全部html頁面增長預約義的footbar一類的工做,或者對輸出的圖片的URL進行替換之類的工做。dom

upstream: upstream模塊實現反向代理的功能,將真正的請求轉發到後端服務器上,並從後端服務器上讀取響應,發回客戶端。upstream模塊是一種特殊的handler,只不過響應內容不是真正由本身產生的,而是從後端服務器上讀取的。socket

load-balancer: 負載均衡模塊,實現特定的算法,在衆多的後端服務器中,選擇一個服務器出來做爲某個請求的轉發服務器。

三,nginx的請求處理


nginx使用一個多進程模型來對外提供服務,其中一個master進程,多個worker進程。master進程負責管理nginx自己和其餘worker進程。

全部實際上的業務處理邏輯都在worker進程。worker進程中有一個函數,執行無限循環,不斷處理收到的來自客戶端的請求,並進行處理,直到整個nginx服務被中止。

worker進程中,ngx_worker_process_cycle()函數就是這個無限循環的處理函數。在這個函數中,一個請求的簡單處理流程以下:

#) 操做系統提供的機制(例如epoll, kqueue等)產生相關的事件。
#) 接收和處理這些事件,如是接受到數據,則產生更高層的request對象。
#) 處理request的header和body。
#) 產生響應,併發送回客戶端。
#) 完成request的處理。
#) 從新初始化定時器及其餘事件。

四,請求的處理流程
 

爲了讓你們更好的瞭解nginx中請求處理過程,咱們以HTTP Request爲例,來作一下詳細地說明。

從nginx的內部來看,一個HTTP Request的處理過程涉及到如下幾個階段。

#) 初始化HTTP Request(讀取來自客戶端的數據,生成HTTP Request對象,該對象含有該請求全部的信息)。
#) 處理請求頭。
#) 處理請求體。
#) 若是有的話,調用與此請求(URL或者Location)關聯的handler。
#) 依次調用各phase handler進行處理。

在這裏,咱們須要瞭解一下phase handler這個概念。phase字面的意思,就是階段。因此phase handlers也就好理解了,就是包含若干個處理階段的一些handler。

在每個階段,包含有若干個handler,再處理到某個階段的時候,依次調用該階段的handler對HTTP Request進行處理。

一般狀況下,一個phase handler對這個request進行處理,併產生一些輸出。一般phase handler是與定義在配置文件中的某個location相關聯的。

一個phase handler一般執行如下幾項任務:

#) 獲取location配置。
#) 產生適當的響應。
#) 發送response header。
#) 發送response body。


當nginx讀取到一個HTTP Request的header的時候,nginx首先查找與這個請求關聯的虛擬主機的配置。若是找到了這個虛擬主機的配置,那麼一般狀況下,這個HTTP Request將會通過如下幾個階段的處理(phase handlers):

NGX_HTTP_POST_READ_PHASE:      讀取請求內容階段
NGX_HTTP_SERVER_REWRITE_PHASE: Server請求地址重寫階段
NGX_HTTP_FIND_CONFIG_PHASE:    配置查找階段:
NGX_HTTP_REWRITE_PHASE:        Location請求地址重寫階段
NGX_HTTP_POST_REWRITE_PHASE:   請求地址重寫提交階段
NGX_HTTP_PREACCESS_PHASE:      訪問權限檢查準備階段
NGX_HTTP_ACCESS_PHASE: 訪問權限檢查階段
NGX_HTTP_POST_ACCESS_PHASE:    訪問權限檢查提交階段
NGX_HTTP_TRY_FILES_PHASE:      配置項try_files處理階段
NGX_HTTP_CONTENT_PHASE:        內容產生階段
NGX_HTTP_LOG_PHASE:    日誌模塊處理階段


在內容產生階段,爲了給一個request產生正確的響應,nginx必須把這個request交給一個合適的content handler去處理。若是這個request對應的location在配置文件中被明確指定了一個content handler,那麼nginx就能夠經過對location的匹配,直接找到這個對應的handler,並把這個request交給這個content handler去處理。這樣的配置指令包括像perl,flv,proxy_pass,mp4等。

若是一個request對應的location並無直接有配置的content handler,那麼nginx依次嘗試:

#) 若是一個location裏面有配置random_index on,那麼隨機選擇一個文件,發送給客戶端。
#) 若是一個location裏面有配置index指令,那麼發送index指令指明的文件,給客戶端。
#) 若是一個location裏面有配置autoindex on,那麼就發送請求地址對應的服務端路徑下的文件列表給客戶端。
#) 若是這個request對應的location上有設置gzip_static on,那麼就查找是否有對應的.gz文件存在,有的話,就發送這個給客戶端(客戶端支持gzip的狀況下)。
#) 請求的URI若是對應一個靜態文件,static module就發送靜態文件的內容到客戶端。

內容產生階段完成之後,生成的輸出會被傳遞到filter模塊去進行處理。filter模塊也是與location相關的。全部的fiter模塊都被組織成一條鏈。輸出會依次穿越全部的filter,直到有一個filter模塊的返回值代表已經處理完成。

這裏列舉幾個常見的filter模塊,例如:

#) server-side includes。
#) XSLT filtering。
#) 圖像縮放之類的。
#) gzip壓縮。


在全部的filter中,有幾個filter模塊須要關注一下。按照調用的順序依次說明以下:

write: 寫輸出到客戶端,其實是寫到鏈接對應的socket上。 postpone: 這個filter是負責subrequest的,也就是子請求的。 copy: 將一些須要複製的buf(文件或者內存)從新複製一份而後交給剩餘的body filter處理。  

相關文章
相關標籤/搜索