Principles of nginx phase handler and types of phase Handler
After nginx receives and parses the request line, it calls each phase handler in turn after the request header. Phase handler is the stage to complete nginx's main functions.
Nginx has the following 11 types of phase, which are executed in sequence. Multiple handler may be attached to the same phase. WhereItalic boldThe user-defined handler cannot be mounted.
Phase |
Remarks |
Ngx_http_post_read_phase |
Read Request content stage |
Ngx_http_server_rewrite_phase |
Server Request address rewriting stage |
Ngx_http_find_config_phase |
Configuration search stage |
Ngx_http_rewrite_phase |
Location request address rewriting stage |
Ngx_http_post_rewrite_phase |
Request address rewriting submission stage |
Ngx_http_preaccess_phase |
Access permission check preparation stage |
Ngx_http_access_phase |
Access permission check phase |
Ngx_http_post_access_phase |
Access permission check submission stage |
Ngx_http_try_files_phase |
Configuration item try_files processing stage |
Ngx_http_content_phase |
Content generation phase |
Ngx_http_log_phase |
Log Module processing phase |
How to register phase Handler
Generally, most of our custom modules are mounted in the ngx_http_content_phase stage. The mounting action is generally in the postconfiguration function called by the module context.
The Mount code example is as follows:
Static aggregate (ngx_conf_t * Cf) // postconfiguration hook point {ngx_http_handler_pt * h; ngx_http_core_main_conf_t * colap; colap = aggregate (CF, ngx_http_core_module ); H = ngx_array_push (& colap-> phases [ngx_http_content_phase]. handlers); If (H = NULL) {return ngx_error;} * H = ngx_http_hello_handler; return ngx_ OK ;}
Colap-> phases [ngx_http_content_phase]. handlers is the handler array of the content phase stage, similar:
Colap-> phases [ngx_http_server_rewrite_phase]. handlers
Colap-> phases [ngx_http_rewrite_phase]. handlers
Colap-> phases [ngx_http_preaccess_phase]. handlers
...
Each configurable phase has a phase handler array. You can choose to mount it in different phase arrays.
When nginx parses the HTTP configuration, it will combine multiple phase handler arrays into an array.
Static char * ngx_http_block (ngx_conf_t * Cf, ngx_command_t * cmd, void * conf) // hook function {of the HTTP command {... For (m = 0; ngx_modules [m]; m ++) {If (ngx_modules [m]-> type! = Ngx_http_module) {continue;} module = ngx_modules [m]-> CTX; If (module-> postconfiguration) {If (module-> postconfiguration (CF )! = Ngx_ OK) {// execute the postconfigure hook of each module. Phase handler will mount return ngx_conf_error ;}} at this time ;}}}... If (ngx_http_init_phase_handlers (CF, colap )! = Ngx_ OK) {// combine multiple phase handler arrays into an array return ngx_conf_error ;}...}
The ngx_http_init_phase_handlers (CF, colap) function combines several phase handler arrays (except log phase) into an ngx_http_phase_handler_t array.
Struct handler {ngx_http_phase_handler_pt checker; // check the handler return result and decide the handler ngx_http_handler_pt handler to be executed next; // handler hook ngx_uint_t next; // point to the first handler of the next phase };
The following are different phase corresponding to different checker functions:
Phase |
Checker |
Ngx_http_post_read_phase |
Ngx_http_core_generic_phase |
Ngx_http_server_rewrite_phase |
Ngx_http_core_rewrite_phase |
Ngx_http_find_config_phase |
Ngx_http_core_find_config_phase |
Ngx_http_rewrite_phase |
Ngx_http_core_rewrite_phase |
Ngx_http_post_rewrite_phase |
Ngx_http_core_post_rewrite_phase |
Ngx_http_preaccess_phase |
Ngx_http_core_generic_phase |
Ngx_http_access_phase |
Ngx_http_core_access_phase |
Ngx_http_post_access_phase |
Ngx_http_core_post_access_phase |
Ngx_http_try_files_phase |
Ngx_http_core_try_files_phase |
Ngx_http_content_phase |
Ngx_http_core_content_phase |
Ngx_http_log_phase |
Ngx_http_core_generic_phase |
How to execute phase Handler
Nginx receives and parses the request line. After the request header, it calls each phase handler in turn.
voidngx_http_core_run_phases(ngx_http_request_t *r){ ngx_int_t rc; ngx_http_phase_handler_t *ph; ngx_http_core_main_conf_t *cmcf; cmcf = ngx_http_get_module_main_conf(r, ngx_http_core_module); ph = cmcf->phase_engine.handlers; while (ph[r->phase_handler].checker) { rc = ph[r->phase_handler].checker(r, &ph[r->phase_handler]); if (rc == NGX_OK) { return; } }}
As you can see, what we execute in sequence is the ngx_http_phase_handler_t array generated in the initialization phase.
Through debug, let's take a look at the actual content of the ngx_http_phase_handler_t array.
Contents of the PH array during running |
Array subscript |
Checker |
Handler |
Next |
0 |
Ngx_http_core_rewrite_phase |
Ngx_http_rewrite_handler |
1 |
1 |
Ngx_http_core_find_config_phase |
0 |
0 |
2 |
Ngx_http_core_rewrite_phase |
Ngx_http_rewrite_handler |
3 |
3 |
Ngx_http_core_post_rewrite_phase |
0 |
1 |
4 |
Ngx_http_core_generic_phase |
Ngx_http_l7waf_handler |
7 |
5 |
Ngx_http_core_generic_phase |
Ngx_http_limit_req_handler |
7 |
6 |
Ngx_http_core_generic_phase |
Ngx_http_limit_conn_handler |
7 |
7 |
Ngx_http_core_access_phase |
Ngx_http_access_handler |
10 |
8 |
Ngx_http_core_access_phase |
Ngx_http_auth_basic_handler |
10 |
9 |
Ngx_http_core_post_access_phase |
0 |
10 |
10 |
Ngx_http_core_try_files_phase |
0 |
0 |
11 |
Ngx_http_core_content_phase |
Ngx_http_index_handler |
14 |
12 |
Ngx_http_core_content_phase |
Ngx_http_autoindex_handler |
14 |
13 |
Ngx_http_core_content_phase |
Ngx_http_static_handler |
14 |
14 |
0 |
0 |
0 |
Let's look at a specific checker function.
Compile (ngx_http_request_t * r, prepare * pH) {ngx_int_t RC;/** generic phase checker, * used by the post read and pre-access phases */ngx_log_debug1 (ngx_log_debug_http, r-> connection-> log, 0, "generic phase: % UI", R-> phase_handler); rc = Ph-> handler (R ); // execute the mounted handler if (rc = ngx_ OK) {// The returned value is ngx_ OK, indicating that the phase is finished and jumps to the first handler of the next phase to R-> phase_han Dler = Ph-> next; return ngx_again;} If (rc = ngx_declined) {// return ngx_declined, continue executing the next handler R-> phase_handler ++ of this phase; return ngx_again;} If (rc = ngx_again | rc = ngx_done) {// indicates that the request has been processed. All the following phase handler does not need to execute return ngx_ OK;}/* rc = ngx_error | rc = ngx_http _... */ngx_http_finalize_request (R, RC); // return an error, end the request, and return the corresponding error page return ngx_ OK ;}
How to select which phase
Read Request content stage
There is no default handler in this phase. It is mainly used to read the Request body and process the Request body accordingly.
Server Request address rewriting stage
This phase mainly deals with global (server block) rewrite rules.
Configuration search stage
In this phase, Uri is used to find the corresponding location. Then, associate the URI and location data. In this phase, the main processing logic is in the checker function,Custom Handler cannot be mounted.
Location request address rewriting stage
This mainly deals with the rewrite of location block.
Request address rewriting submission stage
Post rewrite, which mainly performs some verification and final work, so that it can be handed over to the subsequent modules.This phase cannot mount a Custom Handler.
Access permission check preparation stage
For example, the access type of traffic control is stored in the phase, that is, it mainly performs some coarse-grained access.
Access permission check phase
For example, for access control, permission verification is stored in the phase. Generally, the processing action is handed over to the following module. This is mainly for some fine-grained access.
Access permission check submission stage
Generally, after the access module obtains the access_code, it will perform operations based on the access_code.This phase cannot mount a Custom Handler.
Configuration item try_files processing stage
The try_file module corresponds to the try_files command in the configuration file.This phase cannot mount a Custom Handler.
Check whether the file exists in sequence and return the first file found. The slash at the end of the slash is the folder-$ uri /. If none of the files can be found, an internal redirection will be performed to the last parameter.
Content generation phase
The content processing module generates file content. If it is Php, it calls phpcgi. If it is a proxy, it is forwarded to the corresponding backend server.
Log Module processing phase
The log processing module is executed at the end of each request. Used to print access logs.
Through the above analysis of phase handler, we can know that nginx is divided into different phase, and different functions are arranged for different sequential execution.
Select the phase to which the handler is attached, select the handler execution sequence, and select different checker functions.
Custom Handler can sometimes be mounted to different phase to run normally.
If the Custom Handler depends on the result of a phase, it must be mounted to the phase following the phase.
Custom Handler must follow nginx's functional division for different phase, but not required.
Except for four phase files that cannot be attached and log phase files, the following six phase files can be attached:
Ngx_http_post_read_phase
Ngx_http_server_rewrite_phase
Ngx_http_rewrite_phase
Ngx_http_preaccess_phase
Ngx_http_access_phase
Ngx_http_content_phase
Many functions can be attached to these six phase files. Mounting on the front will improve our performance. mounting on the back will increase our degree of freedom.
For example, if we implement the ngx_http_post_read_phase stage, we cannot combine the commands implemented in subsequent stages of location if to implement more complex functions.
Recommended
Ngx_http_preaccess_phase
Ngx_http_access_phase
Ngx_http_content_phase
Principles and selection of nginx phase Handler