Skip to content

Commit bcb1b5a

Browse files
committed
整理模块代码流程 按照Nginx官方规范流程
1 parent 8851faa commit bcb1b5a

File tree

3 files changed

+123
-80
lines changed

3 files changed

+123
-80
lines changed

README.md

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -53,4 +53,10 @@ typedef struct {
5353
![image](https://ws2.sinaimg.cn/large/005LOzcmly1fgjfosnvf5j31hy0q6wlb.jpg)
5454

5555
## Combination Nginx module
56-
![image](https://ws2.sinaimg.cn/large/005LOzcmly1fgjjo2l11jj31en0g4gq1.jpg)
56+
![image](https://ws2.sinaimg.cn/large/005LOzcmly1fgjjo2l11jj31en0g4gq1.jpg)
57+
58+
>reference
59+
[1] Evan Miller, Emiller's Guide To Nginx Module Development. http://www.evanmiller.org/nginx-modules-guide.html, 2009
60+
[2] http://wiki.nginx.org/Configuration
61+
[3] Clément Nedelcu, Nginx Http Server. Packt Publishing, 2010
62+
[4] codinglabs http://blog.codinglabs.org/articles/intro-of-nginx-module-development.html

README_zh.md

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -52,4 +52,10 @@ typedef struct {
5252
![image](https://ws2.sinaimg.cn/large/005LOzcmly1fgjfosnvf5j31hy0q6wlb.jpg)
5353

5454
## 组合Nginx Module
55-
![image](https://ws2.sinaimg.cn/large/005LOzcmly1fgjjo2l11jj31en0g4gq1.jpg)
55+
![image](https://ws2.sinaimg.cn/large/005LOzcmly1fgjjo2l11jj31en0g4gq1.jpg)
56+
57+
>参考文献
58+
[1] Evan Miller, Emiller's Guide To Nginx Module Development. http://www.evanmiller.org/nginx-modules-guide.html, 2009
59+
[2] http://wiki.nginx.org/Configuration
60+
[3] Clément Nedelcu, Nginx Http Server. Packt Publishing, 2010
61+
[4] codinglabs http://blog.codinglabs.org/articles/intro-of-nginx-module-development.html

src/nginx_moudle_echo.c

Lines changed: 109 additions & 78 deletions
Original file line numberDiff line numberDiff line change
@@ -14,22 +14,21 @@
1414
#include <ngx_core.h>
1515
#include <ngx_http.h>
1616

17-
//定义模块配置结构 命名规则为ngx_http_[module-name]_[main|srv|loc]_conf_t。其中main、srv和loc分别用于表示同一模块在三层block中的配置信息。
17+
/**
18+
* 定义模块配置结构 命名规则为ngx_http_[module-name]_[main|srv|loc]_conf_t。其中main、srv和loc分别用于表示同一模块在三层block中的配置信息。
19+
*/
1820
typedef struct {
1921
ngx_str_t ed; //该结构体定义在这里 https://github.com/nginx/nginx/blob/master/src/core/ngx_string.h
2022
} ngx_http_echo_loc_conf_t;
2123

22-
/*//定义指令 ngx_command_s定义在core/ngx_config_file.h中
23-
struct ngx_command_s {
24-
ngx_str_t name; //词条指令的名称
25-
ngx_uint_t type; //使用掩码标志位方式配置指令参数 具体参考https://github.com/nginx/nginx/blob/master/src/core/ngx_conf_file.h
26-
char *(*set)(ngx_conf_t *cf, ngx_command_t *cmd, void *conf); //set是一个函数指针 用于指导一个参数化函数 具体参考https://github.com/nginx/nginx/blob/master/src/core/ngx_conf_file.h
27-
ngx_uint_t conf; //指定Nginx相应配置文件内存其实地址,一般可以通过内置常量指定,如NGX_HTTP_LOC_CONF_OFFSET,offset指定此条指令的参数的偏移量。
28-
ngx_uint_t offset;
29-
void *post;
30-
};*/
31-
32-
//定义echo模块的指令
24+
static char *ngx_http_echo(ngx_conf_t *cf, ngx_command_t *cmd, void *conf);
25+
static void *ngx_http_echo_create_loc_conf(ngx_conf_t *cf);
26+
static char *ngx_http_echo_merge_loc_conf(ngx_conf_t *cf, void *parent, void *child);
27+
static ngx_int_t ngx_http_echo_init(ngx_conf_t *cf);
28+
29+
/**
30+
* 定义echo模块的指令
31+
*/
3332
static ngx_command_t ngx_http_echo_commands[] = {
3433
{ngx_string("echo"),
3534
NGX_HTTP_LOC_CONF | NGX_CONF_TAKE1,
@@ -41,18 +40,6 @@ static ngx_command_t ngx_http_echo_commands[] = {
4140
ngx_null_command,
4241
};
4342

44-
//参数转化函数
45-
static char *
46-
ngx_http_echo(ngx_conf_t *f,ngx_command_t *cmd , void *conf)
47-
{
48-
ngx_http_core_loc_conf_t *clcf;
49-
clcf = ngx_http_conf_get_module_loc_conf(cf,ngx_http_core_module);
50-
clcf->handle = ngx_http_echo_handler; //修改核心模块配置(也就是当前location),将其handler替换为我们自己定义的ngx_http_echo_handler
51-
ngx_conf_set_str_slot(cf,cmf,conf);
52-
return NGX_CONF_OK;
53-
}
54-
55-
//创建合并配置信息 定义模块Context
5643
/**
5744
* 定义ngx_http_module_t类型的结构体变量 命名规则为ngx_http_[module-name]_module_ctx,这个结构主要用于定义各个Hook函数
5845
*
@@ -62,7 +49,7 @@ ngx_http_echo(ngx_conf_t *f,ngx_command_t *cmd , void *conf)
6249
*/
6350
static ngx_http_module_t ngx_http_echo_module_ctx = {
6451
NULL, /* preconfiguration */
65-
NULL, /* postconfiguration */
52+
ngx_http_echo_init, /* postconfiguration */
6653
NULL, /* create main configuration */
6754
NULL, /* init main configuration */
6855
NULL, /* create server configuration */
@@ -72,42 +59,32 @@ static ngx_http_module_t ngx_http_echo_module_ctx = {
7259
};
7360

7461
/**
75-
* 初始化一个配置结构体
76-
* @param cf
77-
* @return
78-
*/
79-
static char *
80-
ngx_http_echo_create_loc_conf(ngx_conf_t *cf)
81-
{
82-
ngx_http_echo_loc_conf_t *conf;
83-
conf = ngx_pcalloc(cf->pool, sizeof(ngx_http_echo_loc_conf_t)); //gx_pcalloc用于在Nginx内存池中分配一块空间,是pcalloc的一个包装
84-
if(conf == NULL) {
85-
return NGX_CONF_ERROR;
86-
}
87-
conf->ed.len = 0;
88-
conf->ed.data = NULL;
89-
return conf;
90-
}
91-
/**
92-
* 将其父block的配置信息合并到此结构体 实现了配置的继承
93-
* @param cf
94-
* @param parent
95-
* @param child
96-
* @return ngx status code
62+
* 组合Nginx Module
63+
*
64+
* 上面完成了Nginx模块各种组件的开发下面就是将这些组合起来了。一个Nginx模块被定义为一个ngx_module_t结构体https://github.com/nginx/nginx/blob/master/src/core/ngx_module.h,这个结构体的字段很多,不过开头和结尾若干字段一般可以通过Nginx内置的宏去填充
65+
*
66+
* 开头和结尾分别用NGX_MODULE_V1和NGX_MODULE_V1_PADDING 填充了若干字段,就不去深究了。
67+
* 这里主要需要填入的信息从上到下以依次为context、指令数组、模块类型以及若干特定事件的回调处理函数(不需要可以置为NULL),
68+
* 其中内容还是比较好理解的,注意我们的echo是一个HTTP模块,所以这里类型是NGX_HTTP_MODULE,其它可用类型还有NGX_EVENT_MODULE(事件处理模块)和NGX_MAIL_MODULE(邮件模块)。
9769
*
98-
* ngx_conf_merge_str_value不是一个函数,而是一个宏,其定义在https://github.com/nginx/nginx/blob/master/src/core/ngx_conf_file.h#L205中
9970
*/
100-
static char *
101-
ngx_http_echo_merge_loc_conf(ngx_conf_t *cf, void *parent, void *child)
102-
{
103-
ngx_http_echo_loc_conf_t *prev = parent;
104-
ngx_http_echo_loc_conf_t *conf = child;
105-
ngx_conf_merge_str_value(conf->ed, prev->ed, '"');
106-
return NGX_CONF_OK;
107-
}
71+
ngx_module_t ngx_http_echo_module = {
72+
NGX_MODULE_V1,
73+
&ngx_http_echo_module_ctx, /* module context */
74+
ngx_http_echo_commands, /* module directives */
75+
NGX_HTTP_MODULE, /* module type */
76+
NULL, /* init master */
77+
NULL, /* init module */
78+
NULL, /* init process */
79+
NULL, /* init thread */
80+
NULL, /* exit thread */
81+
NULL, /* exit process */
82+
NULL, /* exi master */
83+
NGX_MODULE_V1_PADDING
84+
};
10885

10986
/**
110-
* handler会接收一个ngx_http_request_t指针类型的参数,这个参数指向一个ngx_http_request_t结构体,此结构体存储了这次HTTP请求的一些信息,这个结构定义在https://github.com/nginx/nginx/blob/master/src/http/ngx_http_request.h中:
87+
* Handler会接收一个ngx_http_request_t指针类型的参数,这个参数指向一个ngx_http_request_t结构体,此结构体存储了这次HTTP请求的一些信息,这个结构定义在https://github.com/nginx/nginx/blob/master/src/http/ngx_http_request.h中:
11188
*
11289
* 第一步是获取模块配置信息,这一块只要简单使用ngx_http_get_module_loc_conf就可以了。
11390
*
@@ -164,29 +141,83 @@ ngx_http_echo_handler(ngx_http_request_t *r)
164141
}
165142

166143
/**
167-
* 组合Nginx Module
168-
*
169-
* 上面完成了Nginx模块各种组件的开发下面就是将这些组合起来了。一个Nginx模块被定义为一个ngx_module_t结构体https://github.com/nginx/nginx/blob/master/src/core/ngx_module.h,这个结构体的字段很多,不过开头和结尾若干字段一般可以通过Nginx内置的宏去填充
170-
*
171-
* 开头和结尾分别用NGX_MODULE_V1和NGX_MODULE_V1_PADDING 填充了若干字段,就不去深究了。
172-
* 这里主要需要填入的信息从上到下以依次为context、指令数组、模块类型以及若干特定事件的回调处理函数(不需要可以置为NULL),
173-
* 其中内容还是比较好理解的,注意我们的echo是一个HTTP模块,所以这里类型是NGX_HTTP_MODULE,其它可用类型还有NGX_EVENT_MODULE(事件处理模块)和NGX_MAIL_MODULE(邮件模块)。
144+
* 参数转化函数
145+
* @param f
146+
* @param cmd
147+
* @param conf
148+
* @return ngx status code
149+
*/
150+
static char *
151+
ngx_http_echo(ngx_conf_t *f,ngx_command_t *cmd , void *conf)
152+
{
153+
ngx_http_core_loc_conf_t *clcf;
154+
clcf = ngx_http_conf_get_module_loc_conf(cf,ngx_http_core_module);
155+
clcf->handle = ngx_http_echo_handler; //修改核心模块配置(也就是当前location),将其handler替换为我们自己定义的ngx_http_echo_handler
156+
ngx_conf_set_str_slot(cf,cmf,conf);
157+
return NGX_CONF_OK;
158+
}
159+
160+
161+
162+
/**
163+
* 初始化一个配置结构体
164+
* @param cf
165+
* @return
166+
*/
167+
static char *
168+
ngx_http_echo_create_loc_conf(ngx_conf_t *cf)
169+
{
170+
ngx_http_echo_loc_conf_t *conf;
171+
conf = ngx_pcalloc(cf->pool, sizeof(ngx_http_echo_loc_conf_t)); //gx_pcalloc用于在Nginx内存池中分配一块空间,是pcalloc的一个包装
172+
if(conf == NULL) {
173+
return NGX_CONF_ERROR;
174+
}
175+
conf->ed.len = 0;
176+
conf->ed.data = NULL;
177+
return conf;
178+
}
179+
/**
180+
* 将其父block的配置信息合并到此结构体 实现了配置的继承
181+
* @param cf
182+
* @param parent
183+
* @param child
184+
* @return ngx status code
174185
*
186+
* ngx_conf_merge_str_value不是一个函数,而是一个宏,其定义在https://github.com/nginx/nginx/blob/master/src/core/ngx_conf_file.h#L205中
175187
*/
176-
ngx_module_t ngx_http_echo_module = {
177-
NGX_MODULE_V1,
178-
&ngx_http_echo_module_ctx, /* module context */
179-
ngx_http_echo_commands, /* module directives */
180-
NGX_HTTP_MODULE, /* module type */
181-
NULL, /* init master */
182-
NULL, /* init module */
183-
NULL, /* init process */
184-
NULL, /* init thread */
185-
NULL, /* exit thread */
186-
NULL, /* exit process */
187-
NULL, /* exit master */
188-
NGX_MODULE_V1_PADDING
189-
};
188+
static char *
189+
ngx_http_echo_merge_loc_conf(ngx_conf_t *cf, void *parent, void *child)
190+
{
191+
ngx_http_echo_loc_conf_t *prev = parent;
192+
ngx_http_echo_loc_conf_t *conf = child;
193+
ngx_conf_merge_str_value(conf->ed, prev->ed, '"');
194+
return NGX_CONF_OK;
195+
}
196+
197+
/**
198+
* init echo模块
199+
* @param cf
200+
* @return
201+
*/
202+
static ngx_int_t
203+
ngx_http_echo_init(ngx_conf_t *cf)
204+
{
205+
ngx_http_handler_pt *h;
206+
ngx_http_core_main_conf_t *cmcf;
207+
208+
cmcf = ngx_http_conf_get_module_main_conf(cf, ngx_http_core_module);
209+
210+
h = ngx_array_push(&cmcf->phases[NGX_HTTP_CONTENT_PHASE].handlers);
211+
if (h == NULL) {
212+
return NGX_ERROR;
213+
}
214+
215+
*h = ngx_http_echo_handler;
216+
217+
return NGX_OK;
218+
}
219+
220+
190221

191222

192223

0 commit comments

Comments
 (0)