如何開始寫一個模塊
比較特別的有兩點:
1,需要手工寫一個config文件,告訴nginx如何編譯你的模塊
2,需要把你的模塊編譯進去:./configure --prefix=`pwd`/output --add-module=`pwd`/mymod
概述
所謂寫nginx的module,基本上就是寫handler或者filter。
handler主要是用來生成內容的,也會干點其他雜事。
filter主要是用來修改內容的。
關於handler的說明
參見:ngx_http_core_module.c
所謂handler就是在特定的phase會進行調用的回調函數。
handler的初始化在ngx_http_init_phase_handlers
handler的調用在ngx_http_core_run_phases,這個函數最初會在ngx_http_handler進行調用。
模塊可以通過h = ngx_array_push(&cmcf->phases[NGX_HTTP_ACCESS_PHASE].handlers)的方式把自己的回調函數加入到handler鏈表裡面去。
關於http filter的說明
ngx_http_header_filter_module.c是最初的ngx_http_top_header_filter,通常會在next_header_filter的最後進行調用。它會有條件的設置content-length等字段,並調用ngx_http_write_filter()進行發送。
ngx_http_write_filter_module.c是一個特別的module,負責進行實際的發送。這個模塊是最初的ngx_http_top_body_filter,通常會在next_header_filter和next_body_filter的最後進行調用。
注意:一旦調用了next_filter,就可能會一路next_filter到write_filter_module,然後如果滿足了發送條件就會進行實際的數據發送;一旦數據發送,則http headers就不能再修改了。
如何讀取request的各個字段做處理
可以參見:ngx_http_request_s裡面的headers_in
可以搜索:r->headers_in
直接讀取裡面的各個字段就可以了,比如r->headers_in.cookies是cookie列表。
如何修改response header
類似的,response header位於r->headers_out,直接修改就ok了。
但是注意,修改response header必須在調用ngx_next_http_header_filter之前。
因為一旦next filter了就可能數據已經發出去了,已經發出去了的數據是沒法修改的。
如何修改response body www.2cto.com
由於通常都會需要修改http body的長度,因此有兩種方法:
1,用ngx_http_clear_content_length()清除content-length,然後立刻調用next_header_filter,從而使得數據以trunked的方式發送。參見:ngx_http_gzip_filter_module.c
2,在header filter裡面不調next_header_filter,而是等body都處理完之後,設置了r->headers_out.content_length,再調next_header_filter。參見:ngx_http_image_filter_module.c
這兩種方式各有優缺點:前者會把response變成trunked的,後者需要把response都hold在內存裡。需要結合具體情況來選擇。
作者:wwwsq