相同的配置项可以在相同的时间内发生的多个块。例如HTTP片、server片、location片。阻断取之于在配置项值。


处理HTTP配置项分下面4个步骤:
  1. 创建数据结构用于存储配置项相应的參数
  2. 设定配置项在配置文件里出现时的限制条件与回调方法
  3. 实现上述回调方法,或使用Nginx预设的14个回调方法
  4. 合并不同级别的同名配置项
1、分配用于保存配置參数的数据结构
创建一个结构体,用来保存感兴趣的參数。比如定义一个以下的结构体:
typedef struct
{
ngx_str_t my_str;
ngx_int_t my_num;
ngx_flag_t my_flag;
size_t my_size;
ngx_array_t* my_str_array;
ngx_array_t* my_keyval;
off_t my_off;
ngx_msec_t my_msec;
time_t my_sec;
ngx_bufs_t my_bufs;
ngx_uint_t my_enum_seq;
ngx_uint_t my_bitmask;
ngx_uint_t my_access;
ngx_path_t* my_path; ngx_str_t my_config_str;
ngx_int_t my_config_num;
} ngx_http_mytest_conf_t;

HTTP框架在解析配置文件nginx.conf时,仅仅要遇到http{}、server{}、location{}。就会分配一个保存參数的结构体。这些结构体由ngx_http_module_t接口中的回调方法生成:
typedef struct {
ngx_int_t (*preconfiguration)(ngx_conf_t *cf); // 解析配置文件前调用
ngx_int_t (*postconfiguration)(ngx_conf_t *cf); // 解析完配置文件后调用 void *(*create_main_conf)(ngx_conf_t *cf); // 创建存储直属于http{}的配置项的结构体
char *(*init_main_conf)(ngx_conf_t *cf, void *conf); // 初始化main级别配置项 void *(*create_srv_conf)(ngx_conf_t *cf); // 创建存储直属于srv{}的配置项的结构体
char *(*merge_srv_conf)(ngx_conf_t *cf, void *prev, void *conf); // 合并main级别和srv级别的同名配置项 void *(*create_loc_conf)(ngx_conf_t *cf); // 创建存储直属于loc{}的配置项的结构体
char *(*merge_loc_conf)(ngx_conf_t *cf, void *prev, void *conf); // 合并srv级别和loc级别的同名配置项
} ngx_http_module_t;

详细步骤例如以下:
  • 发现http{},调用create_main_conf、create_srv_conf、create_loc_conf
  • 发现server{},调用create_srv_conf、create_loc_conf
  • 发现location{}。调用create_loc_conf
普通HTTP模块一般仅仅实现create_loc_conf方法。用以匹配某个URL请求,定义方式例如以下:
static void* ngx_http_mytest_create_loc_conf(ngx_conf_t *cf)
{
ngx_http_mytest_conf_t *mycf; mycf = (ngx_http_mytest_conf_t *)ngx_pcalloc(cf->pool, sizeof(ngx_http_mytest_conf_t));
if (mycf == NULL)
return NULL; mycf->my_flag = NGX_CONF_UNSET;
mycf->my_num = NGX_CONF_UNSET;
mycf->my_str_array = NGX_CONF_UNSET_PTR;
mycf->my_keyval = NULL;
mycf->my_off = NGX_CONF_UNSET;
mycf->my_msec = NGX_CONF_UNSET_MSEC;
mycf->my_sec = NGX_CONF_UNSET;
mycf->my_size = NGX_CONF_UNSET_SIZE; return mycf;
}

2、设定配置项的解析方式
配置项的解析方式由ngx_command_t数组定义:
struct ngx_command_s {
ngx_str_t name; // 配置项名称
ngx_uint_t type; // 配置项类型,包含该配置项能够出现的位置和能够携带參数的个数 // 出现name配置项后,调用此方法解析配置项參数
char *(*set)(ngx_conf_t *cf, ngx_command_t *cmd, void *conf);
ngx_uint_t conf; // 配置文件里的偏移量,确定将该配置项放入哪个存储结构体中
ngx_uint_t offset; // 将该配置项放在存储结构体的哪个字段
void *post; // 配置项读取后的处理方法
};

成员含义例如以下:
  • name:配置项名称
  • type:决定配置项能够在哪些块中出现
  • set:解析配置项的回调方法
  • conf:告诉HTTP框架该配置项參数放在哪个结构体中。取值例如以下:
    • NGX_HTTP_MAIN_CONF_OFFSET:用create_main_conf产生的结构体存储配置项參数
    • NGX_HTTP_SRV_CONF_OFFSET:用create_srv_conf产生的结构体存储配置项參数
    • NGX_HTTP_LOC_CONF_OFFSET:用create_loc_conf产生的结构体存储配置项參数
    • 普通情况下。HTTP模块实现create_loc_conf回调方法。然后把conf设置为NGX_HTTP_LOC_CONF_OFFSET
  • offset:表示当前配置项在整个存储配置项的结构体中的偏移位置。由宏offsetof(struct, member)计算偏移量。

    Nginx的预设解析方法须要通过conf成员确定存储配置项參数结构体。然后通过offset成员确定存储配置项參数的成员。但自己定义解析方法把这一项设为0就可以,由于怎样存储是由我们定义的。

  • post:多用途指针。一般不使用
3、解析配置项的14种预设方法
以ngx_conf_set_flag_slot为例,它用于解析带有on或off參数的配置项,相应的ngx_command_s结构例如以下:
{
ngx_string("test_flag"),
NGX_HTTP_LOC_CONF | NGX_CONF_FLAG,
ngx_conf_set_flag_slot,
NGX_HTTP_LOC_CONF_OFFSET,
offsetof(ngx_http_mytest_conf_t, my_flag),
NULL
},

上述成员中。NGX_CONF_FLAG表示配置项仅仅有一个參数,且仅仅能是on或off。offsetof(ngx_http_mytest_conf_t, my_flag)表示将配置项test_flag后的參数存放在ngx_http_mytest_conf_t结构体的my_flag成员中。


其余13个预设方法类似。

4、自己定义配置项处理方法
该方法的目的就是把感兴趣的配置项參数存入预先分配好的结构体中:
static char* ngx_conf_set_myconfig(ngx_conf_t *cf, ngx_command_t *cmd, void *conf)
{
/* 參数conf就是http框架传给我们的。在ngx_http_mytest_create_loc_conf
* 回调方法中分配的结构体ngx_http_mytest_conf_t
*/
ngx_http_mytest_conf_t *mycf = conf; /* cf->args是1个ngx_array_t队列。它的成员都是ngx_str_t结构。
* 我们用value指向ngx_array_t的elts内容,当中value[1]就是第1
* 个參数,同理value[2]是第2个參数
*/
ngx_str_t* value = cf->args->elts; //ngx_array_t的nelts表示參数的个数
if (cf->args->nelts > 1)
mycf->my_config_str = value[1]; if (cf->args->nelts > 2)
{
mycf->my_config_num = ngx_atoi(value[2].data, value[2].len); /* 字符串转整型 */ //假设字符串转化整型失败,将报"invalid number"错误,nginx启动失败
if (mycf->my_config_num == NGX_ERROR)
return "invalid number";
} return NGX_CONF_OK; //返回成功
}

当存在例如以下ngx_command_s时:
{
ngx_string("test_myconfig"),
NGX_HTTP_LOC_CONF | NGX_CONF_TAKE12,
ngx_conf_set_myconfig,
NGX_HTTP_LOC_CONF_OFFSET,
0,
NULL
},

当在配置文件里出现test_myconfig配置项时,会调用我们自己定义的ngx_conf_set_myconfig方法解析配置项,存储配置项參数。比如:
test_myconfig test 123
那么解析完之后:
mycf->my_config_str = test
mycf->my_config_num = 123

5、配置项合并
若ngx_http_module_t.merge_loc_conf为NULL,那么外层配置块http{]和server{}中同名配置项都不会生效。所以,假设须要合并同名配置项,则定义merge_loc_conf函数。merge_srv_conf函数原理同样。怎样合并是自由的,比如merge_loc_conf能够例如以下定义:
static char * ngx_http_mytest_merge_loc_conf(ngx_conf_t *cf, void *parent, void *child)
{
/* parent指向父配置块相应结构体。child指向子配置块相应结构体 */
ngx_http_mytest_conf_t *prev = (ngx_http_mytest_conf_t *)parent;
ngx_http_mytest_conf_t *conf = (ngx_http_mytest_conf_t *)child; /* conf = prev或"defaultstr" */
ngx_conf_merge_str_value(conf->my_str, prev->my_str, "defaultstr"); /* conf = prev或0 */
ngx_conf_merge_value(conf->my_flag, prev->my_flag, 0); return NGX_CONF_OK;
}

有10种合并配置项的方法,ngx_conf_merge_str_value和ngx_conf_merge_value是当中的两个。


參考:
《深入了解Nginx》 P115-P140.

版权声明:本文博客原创文章,博客,未经同意,不得转载。

【Nginx】如何应对HTTP组态的更多相关文章

  1. 借助nginx搭建反向代理服务器小例

    1 反向代理: 反向代理(Reverse Proxy)方式是指以代理服务器接收internet上的连接请求,然后将请求转发给内部网络上的服务器,并将从服务器上得到的结果返回给internet上请求连接 ...

  2. Nginx 防止SQL注入、XSS攻击的实践配置方法

    下班的时候,发现博客访问缓慢,甚至出现504错误,通过 top -i 命令查看服务器负载发现负载数值飙升到3.2之多了,并且持续时间越来越频繁直至持续升高的趋势,还以为是被攻击了,对来访IP进行了阈值 ...

  3. Nginx高并发配置思路(轻松应对1万并发量)

    测试机器为腾讯云服务器1核1G内存,swap分区2G,停用除SSH外的所有服务,仅保留nginx,优化思路主要包括两个层面:系统层面+nginx层面. 一.系统层面 1.调整同时打开文件数量 ulim ...

  4. Nginx优化具体,应对高并发

     nginx指令中的优化(配置文件) worker_processes 8; nginx进程数,建议依照cpu数目来指定.一般为它的倍数. worker_cpu_affinity 00000001 ...

  5. Nginx优化配置,轻松应对高并发

    Nginx现在已经是最火的web服务器之一,尤其在静态分离和负载均衡方面,性能十分优越.接下来我们主要看下Nginx在高并发环境下的优化配置,主要是针对 nginx.conf 文件的属性设置.我们打开 ...

  6. nginx+php 在windows下的简单配置安装

    开始前的准备 PHP安装包下载:http://windows.php.net/downloads/releases/php-5.5.14-Win32-VC11-x86.zip Nginx 下载地址:h ...

  7. 织梦Dedecms使用Nginx的安全设置

    首先需要说明的是,任何程序都是有漏洞的,我们需要做好一些必要的防范,来减少由于程序漏洞造成的损失.织梦的漏洞多,这个是很多人的想法.不过大家如果做好了织梦系统的文件夹权限什么的设置,很多漏洞也是用不上 ...

  8. Apache与Nginx对客户端请求的处理机制对比

    Apache与Nginx对客户端请求的处理机制对比 模块 大致为四个模块,核心模块.HTTP模块.邮件模块,以及第三方模块 核心模块主要包含两类功能的支持,一类是主体功能,包括进程管理,权限管理,错误 ...

  9. 从Nginx的Web请求处理机制中剖析多进程、多线程、异步IO

    Nginx服务器web请求处理机制 从设计架构来说,Nginx服务器是与众不同的.不同之处一方面体现在它的模块化设计,另一方面,也是最重要的一方面,体现在它对客户端请求的处理机制上. Web服务器和客 ...

随机推荐

  1. ZOJ 3822 Domination(概率dp 牡丹江现场赛)

    题目链接:problemId=5376">http://acm.zju.edu.cn/onlinejudge/showProblem.do?problemId=5376 Edward ...

  2. 改动EditPlus默认模板

    watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvY2FvaGFpY2hlbmc=/font/5a6L5L2T/fontsize/400/fill/I0JBQk ...

  3. oracle看到用户的所有表名、表睐、字段名称、现场的目光、是空的、字段类型

    --oracle看到用户的所有表名.表睐.字段名称.现场的目光.是空的.字段类型 select distinct TABLE_COLUMN.*, TABLE_NALLABLE.DATA_TYPE, T ...

  4. 用JavaScript实现网页动态水印

    1.基本原理 页面加载后,通过javascript创建页面元素div,并在div元素中创建文本节点,展示水印内容 设置div元素样式,将其zIndex设置一个较高的值,并设置透明度,实现浮在页面的水印 ...

  5. HTTPDNS成为移动互联网的标配–原因与原理解析(转)

    DNS,作用就是将域名解析成IP.一个DNS查询,先从本地缓存查找,如果没有或者已经过期,就从DNS服务器查询,如果客户端没有主动设置DNS服务器,一般是从服务商DNS服务器上查找.这就出现了不可控. ...

  6. NSUserDefaults写作和阅读对象定义自己

    需要编写对象必须实现NSCoding protocol Person Class Person.h #import <Foundation/Foundation.h> #import &q ...

  7. HotSpot关联规则算法(2)-- 挖掘连续型和离散型数据

    本篇代码可在 http://download.csdn.net/detail/fansy1990/8502323下载. 前篇<HotSpot关联规则算法(1)-- 挖掘离散型数据>分析了离 ...

  8. 算法入门经典大赛 Dynamic Programming

    111 - History Grading LCS 103 - Stacking Boxes 最多能叠多少个box DAG最长路 10405 - Longest Common Subsequence ...

  9. POJ 3450 Corporate Identity KMP解决问题的方法

    这个问题,需要一组字符串求最长公共子,其实灵活运用KMP高速寻求最长前缀. 请注意,意大利愿父亲:按照输出词典的顺序的规定. 另外要提醒的是:它也被用来KMP为了解决这个问题,但是很多人认为KMP使用 ...

  10. 如何自动以管理员身份运行.NET程序?

    原文:如何自动以管理员身份运行.NET程序? windows 7和vista提高的系统的安全性,同时需要明确指定“以管理员身份运行”才可赋予被运行软件比较高级的权限,比如访问注册表等.否则,当以普通身 ...