一步一步开发nginx核心模块(1)

准备写成nginx核心模块开发实践教程

这篇博客对hello world模块程序(以下简称模块)解释。

1.模块源程序组成

模块源程序分2个文件,1个叫config,另1个叫ngx_core_hw.c。

其中config文件在编译时告诉nginx我们编写的模块的名称,去哪儿找我们写的这个模块的源程序来编译。

ngx_core_hw.c这个就是我们的hello world这个模块的源程序了。

2.config解释

没几行,直接在注释中进行解释了。

#ngx_core_hw_module是我们命名的hello world模块的名称
ngx_addon_name=ngx_core_hw_module

#下面一行将该模块添加到nginx的模块链的最后
CORE_MODULES="$CORE_MODULES ngx_core_hw_module"

#下面这行制定模块源程序的位置
#其中变量$ngx_addon_dir就是在./configure --add-module=../ngx_core_hello_world时
#指定的../ngx_core_hello_world这个目录
NGX_ADDON_SRCS="$NGX_ADDON_SRCS $ngx_addon_dir/ngx_core_hw.c"

3.ngx_core_hw.c解释

一个nginx模块至少需要几个数据结构:

  • 配置指令数据结构,类型是:ngx_command_t
  • 模块上下文数据结构,核心模块的类型是:ngx_core_module_t
    如果是http模块,其上下文数据结构的类型是:ngx_http_module_t
  • 模块本身的数据结构,其类型是: ngx_module_t
  • 最后就是各种结构体里面的其他函数、结构等的实现,此处hello world
    只需要一个实现,就是ngx_core_hw_enable_handler这个函数指针的实现

下面就是对该源程序的具体解释

//开发nginx的模块,至少需include此头文件:ngx_core.h。
#include <ngx_core.h>

//ngx_core_hw_enable_handler这个函数指针指向的是具体执行打印hello world的函数
//三个参数就是nginx规定的此类函数指针的参数
static char *ngx_core_hw_enable_handler(ngx_conf_t *cf, ngx_command_t *cmd, void *conf);

//声明数组ngx_core_hw_commands[],这个数组中的每一个元素都是ngx_command_t类型的
static ngx_command_t  ngx_core_hw_commands[] = {
     //hw意思是hello world

     //下面这个大括号就是ngx_command_t的具体格式
     //第一行,指定"ngx_core_hw_enable"为nginx.conf
     //这个配置文件的命令,意思是遇到这个命令,nginx就会
     //执行这个模块
     //ngx_string是nginx定义的一种字符串,使用起来很方便
    { ngx_string("ngx_core_hw_enable"),

     //NGX_MAIN_CONF意思是上述的配置指令只能出现在nginx.conf的顶级目录下面
     //NGX_CONF_TAKE1意思是这个命令需要带一个参数,我们这个地方需要带的参数是on
      NGX_MAIN_CONF|NGX_CONF_TAKE1,

     //下面就是前述声明的函数指针,这个模块启动后就执行这个函数指针指向的函数
      ngx_core_hw_enable_handler,

     //下面的2个0,null都暂不管,这次用不上
      0,
      0,
      NULL },

    //这个ngx_null_command是一个空的ngx_command_t,里面全是null或0
    ngx_null_command
};

//此表明这个模块是核心模块
//ngx_core_module_t就是nginx的核心模块定义的数据结构
//它的具体定义见大括号内的内容
//ngx_core_hw_module_ctx是hello world这个核心模块的上下文

static ngx_core_module_t  ngx_core_hw_module_ctx = {

  //nchw意思是ngx_core_hello_world
    ngx_string("nchw"),
    NULL,
    NULL
};

//下面就是核心模块ngx_core_hw_module的定义

ngx_module_t  ngx_core_hw_module = {
    //下面这个NGX_MODULE_V1是nginx定义的一个宏
    //定义了nginx模块定义的七个值
    NGX_MODULE_V1,

    //下面这个就是前面定义的上下文数据结构的指针
    &ngx_core_hw_module_ctx,                  /* module context */

    //下面这个就是前面定义的核心模块的命令
    ngx_core_hw_commands,                     /* module directives */

    //这个是模块种类:核心模块,和前面的模块上下文的数据结构
    //是一一对应的
    NGX_CORE_MODULE,                       /* module type */
    NULL,                                  /* init master */
    NULL,                                  /* init module */
    NULL,                                  /* init process */
    NULL,                                  /* init thread */
    NULL,                                  /* exit thread */
    NULL,                                  /* exit process */
    NULL,                                  /* exit master */

    //下面这个也是nginx定义的一个宏,一般不用改
    NGX_MODULE_V1_PADDING
};


//ngx_core_hw_enable_handler这个函数指针的具体实现
static char *ngx_core_hw_enable_handler(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{
    //ngx_str_t是nginx定义的字符串结构体
    ngx_str_t        *value;

    //下面这个等式就取得了配置文件中的
    //ngx_core_hw_enable on;的on或者off这个值
    value = (ngx_str_t *)cf->args->elts;

    //如果判断值是on,那就打印hello world,否则就啥也不干,直接运行nginx
    if (ngx_strcasecmp(value[1].data, (u_char *) "on") == 0) {
              printf("hello world!\n");
    } 

    return (char *)NGX_CONF_OK;
}


添加新评论