Nginx源码分析 - 实战篇 - 编写一个自定义的模块(24)

nginx stream proxy 模块的ssl连接源码分析 本为对 nginx的ngx_stream_proxy_module与上游服务器建立ssl连接的过程进行了详细分析。 阅读详情
AI摘要

本文介绍如何创建自定义的Nginx模块,包括模块目录、配置文件、核心代码的编写,以及如何编译和安装模块。通过示例,演示如何实现一个简单的HTTP请求处理器。

目录

一、创建扩展模块目录

二、创建config文件

三、创建ngx_http_hello_module.c文件

四、修改Nginx.conf文件

五、编译Nginx源码

六、浏览器访问


从前面的篇章中,我们基本了解了Nginx的运行原理。Nginx整个框架都是通过模块的方式,对整个系统进行解耦和扩展。在HTTP的http/modules/目录下,有非常多的关于HTTP协议的模块,每个模块都有不同的功能。

 

接下去我们就需要创建一个自定义的模块。

一、创建扩展模块目录


我们在nginx-1.13.1文件夹下,创建一个/extends/ngx_http_hello_module的目录

 

 

二、创建config文件


我们的模块名称为:ngx_http_hello_module
我们需要创建一个config文件,这样Nginx在编译的时候,会将你自定义的模块编译进去。config文件中配置如下:

ngx_addon_name=ngx_http_hello_module
HTTP_MODULES="$HTTP_MODULES ngx_http_hello_module"
NGX_ADDON_SRCS="$NGX_ADDON_SRCS $ngx_addon_dir/ngx_http_hello_module.c"
 

三、创建ngx_http_hello_module.c文件


创建自定义的模块必须遵守Nginx的模块规范,需要定义:

  • ngx_command_t 命令行解析结构
  • ngx_http_module_t 模块的上下文结构
  • ngx_module_t 模块结构

如果对这几个数据结构还不熟悉,先参照我之前的文章吧。

#include <ngx_config.h>
#include <ngx_core.h>
#include <ngx_http.h>

static ngx_int_t ngx_http_hello_handler(ngx_http_request_t *r);

static char *
ngx_http_hello(ngx_conf_t *cf, ngx_command_t *cmd, void *conf);


/**
 * 处理nginx.conf中的配置命令解析
 * 例如:
 * location /hello {
 *  	hello
 * }
 * 当用户请求:http://127.0.0.1/hello的时候,请求会跳转到hello这个配置上
 * hello的命令行解析回调函数:ngx_http_hello
 */
static ngx_command_t ngx_http_hello_commands[] = {
		{
				ngx_string("hello"),
				NGX_HTTP_MAIN_CONF | NGX_HTTP_SRV_CONF | NGX_HTTP_LOC_CONF | NGX_HTTP_LMT_CONF | NGX_CONF_NOARGS,
				ngx_http_hello,
				NGX_HTTP_LOC_CONF_OFFSET,
				0,
				NULL
		},
		ngx_null_command
};


/**
 * 模块上下文
 */
static ngx_http_module_t ngx_http_hello_module_ctx = { NULL, NULL, NULL, NULL,
		NULL, NULL, NULL, NULL };

/**
 * 模块的定义
 */
ngx_module_t ngx_http_hello_module = {
		NGX_MODULE_V1,
		&ngx_http_hello_module_ctx,
		ngx_http_hello_commands,
		NGX_HTTP_MODULE,
		NULL,
		NULL,
		NULL,
		NULL,
		NULL,
		NULL,
		NULL,
		NGX_MODULE_V1_PADDING
};

/**
 * 命令解析的回调函数
 * 该函数中,主要获取loc的配置,并且设置location中的回调函数handler
 */
static char *
ngx_http_hello(ngx_conf_t *cf, ngx_command_t *cmd, void *conf) {
	ngx_http_core_loc_conf_t *clcf;

	clcf = ngx_http_conf_get_module_loc_conf(cf, ngx_http_core_module);
	/* 设置回调函数。当请求http://127.0.0.1/hello的时候,会调用此回调函数 */
	clcf->handler = ngx_http_hello_handler;

	return NGX_CONF_OK;
}

/**
 * 模块回调函数,输出hello world
 */
static ngx_int_t ngx_http_hello_handler(ngx_http_request_t *r) {
	if (!(r->method & (NGX_HTTP_GET | NGX_HTTP_HEAD))) {
		return NGX_HTTP_NOT_ALLOWED;
	}

	ngx_int_t rc = ngx_http_discard_request_body(r);
	if (rc != NGX_OK) {
		return rc;
	}

	ngx_str_t type = ngx_string("text/plain");
	ngx_str_t response = ngx_string("Hello World");
	r->headers_out.status = NGX_HTTP_OK;
	r->headers_out.content_length_n = response.len;
	r->headers_out.content_type = type;

	rc = ngx_http_send_header(r);
	if (rc == NGX_ERROR || rc > NGX_OK || r->header_only) {
		return rc;
	}

	ngx_buf_t *b;
	b = ngx_create_temp_buf(r->pool, response.len);
	if (b == NULL) {
		return NGX_HTTP_INTERNAL_SERVER_ERROR;
	}

	ngx_memcpy(b->pos, response.data, response.len);
	b->last = b->pos + response.len;
	b->last_buf = 1;

	ngx_chain_t out;
	out.buf = b;
	out.next = NULL;

	return ngx_http_output_filter(r, &out);
}

四、修改Nginx.conf文件


我们需要通过http://127.0.0.1/hello 就能访问到我们自定义的hello模块。所以我们需要修改一下Nginx.conf文件:

        #ngx_http_hello_module.c
        location /hello {
        	hello;
        }

五、编译Nginx源码


编译自定义的模块,需要加上:--add_module=模块文件夹

sudo ./configure --prefix=/Users/zhuli/Documents/code/soft/nginx 
--add-module=/Users/xxx/Documents/code/soft/nginx-1.13.1/extends/ngx_http_hello_module
sudo make && make install

编译后,生成模块数组文件:objs/ngx_modules.c 里面就包含我们自定义的模块

  • 模块数组*ngx_modules[] 中的值就是通过这个文件初始化的
  • 然后通过这个模块数组对每个模块进行初始化
extern ngx_module_t  ngx_http_limit_req_module;
extern ngx_module_t  ngx_http_geo_module;
extern ngx_module_t  ngx_http_map_module;
extern ngx_module_t  ngx_http_split_clients_module;
extern ngx_module_t  ngx_http_referer_module;
extern ngx_module_t  ngx_http_rewrite_module;
extern ngx_module_t  ngx_http_proxy_module;
extern ngx_module_t  ngx_http_fastcgi_module;
extern ngx_module_t  ngx_http_uwsgi_module;
extern ngx_module_t  ngx_http_scgi_module;
extern ngx_module_t  ngx_http_memcached_module;
extern ngx_module_t  ngx_http_empty_gif_module;
extern ngx_module_t  ngx_http_browser_module;
extern ngx_module_t  ngx_http_upstream_hash_module;
extern ngx_module_t  ngx_http_upstream_ip_hash_module;
extern ngx_module_t  ngx_http_upstream_least_conn_module;
extern ngx_module_t  ngx_http_upstream_keepalive_module;
extern ngx_module_t  ngx_http_upstream_zone_module;
extern ngx_module_t  ngx_http_hello_module;
extern ngx_module_t  ngx_http_write_filter_module;
extern ngx_module_t  ngx_http_header_filter_module;
extern ngx_module_t  ngx_http_chunked_filter_module;
extern ngx_module_t  ngx_http_range_header_filter_module;
extern ngx_module_t  ngx_http_gzip_filter_module;
extern ngx_module_t  ngx_http_postpone_filter_module;
extern ngx_module_t  ngx_http_ssi_filter_module;
extern ngx_module_t  ngx_http_charset_filter_module;
extern ngx_module_t  ngx_http_userid_filter_module;
extern ngx_module_t  ngx_http_headers_filter_module;
extern ngx_module_t  ngx_http_copy_filter_module;
extern ngx_module_t  ngx_http_range_body_filter_module;
extern ngx_module_t  ngx_http_not_modified_filter_module;
 

六、浏览器访问


在浏览器中输入http://127.0.0.1/hello 就能访问我们自定义的hello模块了。

 

 

Nginx Upstream模块源码分析(上) Upstream模块是一个很重要的模块,很多其他模块都会使用它来完成对后端服务器的访问, 达到反向代理和负载均衡的效果。例如Fastcgi、Memcached、SessionSticky等。 如果自己实现这部分功能,采用传统的实现方式,很可能会阻塞Nginx降低其性能,因为Nginx是全异步非阻塞的。 所以要想不破坏其优美的架构,就得按照其规范实现很多回调函数,注册这些钩子到Ngin 阅读详情

相关推荐

薛定谔 | 先导化合物优化与相互作用可视化

当获得针对某个靶点的先导分子后,想要在此基础上进行化学结构修饰。为了提升化学改造的成功率可以采用本教程方法进行结构虚拟改造/优化。每用薛定谔处理一个新任务,第一步必须创建新的project以方便日后管理。选项卡中修改工作路径(可以方便地找到输出文件)

药研猿的博客 2144

一、nginx自定义路径和模块安装[源码目录结构、自定义configure配置路径和模块]

解释:可通过将下面参数在源码安装nginx执行./configure + 下面参数实现自定义路径,查看可以添加的命令--prefix = PATH (默认位置/usr/local/nginx)存放nginx安装文件的位置(不一定存放核心二进制文件(取决于--sbin-path),其里面一般html、动态模块软链等等)

黑日里不灭的light 3052

数码管动态扫描避坑指南:如何用188芯片实现50Hz无闪烁显示?

本文深入解析188数码管动态扫描技术,提供工业级无闪烁显示方案。通过优化轮询扫描机制、硬件电路设计和软件架构,实现50Hz高刷新率显示,解决亮度不均和鬼影问题,适用于医疗设备和工业控制面板等高要求场景。

hhh00的博客 975

【Nginx】Nginx新增自定义模块

系统环境 [root@localhost nginx]# uname -a Linux localhost.localdomain 3.10.0-1160.el7.x86_64 #1 SMP Mon Oct 19 16:18:59 UTC 2020 x86_64 x86_64 x86_64 GNU/Linux 业务模块 实现一个统计客户端查看资源次数的业务模块。 创建目录 [root@localhost nginx]# cd /home/ronghui/nginx/ [root@localhost ngi

Leoh的博客 1700

virtuoso根据原理图绘制版图并联接_virtuoso画原理图

Virtuoso Schematic Editor 电路仿真一、Virtuoso Schematic Editor 实验目的:掌握电原理图(schematic)设计输入方法。 [1]启动 IC Design 软件 启动 软件: 开机后运行......2.绘制原理图 新建工程后打开的是默认的原理图文件 SCHEMATIC1 PAG...存盘 完成原理图的绘制后,将原理图存盘. 三 . 用 Check...

weixin_33536190的博客 4144

Win11上WSL2安装Ubuntu22.04避坑指南:从镜像源到C++环境配置

本文详细介绍了在Win11系统上安装和配置WSL2及Ubuntu22.04开发环境的完整流程与避坑指南。内容涵盖从解决网络安装错误、更换国内镜像源以加速软件更新,到一站式配置C++开发工具链(包括GCC、GDB、CMake等),并提供了提升WSL2使用体验的实用技巧和故障排除方法,帮助开发者高效搭建稳定的Linux开发环境。

weixin_29306261的博客 474

go语言写的编译成了二进制文件如何查看源代码_Golang自学准备篇:如何快速调试Go语言

Go 语言作为开源项目,我们可以很轻松地获取它的源代码,作为一门编程语言,它有着非常复杂的项目结构和庞大的代码库,今天的 Go 语言项目中差不多有 150 万行源代码,其中包含将近 140 万行的 Go 语言,我们可以使用如下所示的命令查看 Go 语言的代码行数:$ cloc src 5988 text files. 5875 unique files. 1165 file...

weixin_39846191的博客 1291

source tree clone error:fatal remote error: Repository not found

source tree clone error:fatal remote error: Repository not found

Linda的前端开发路 3077

ngnix添加自定义模块

使用msys生成makefile文件时候,configure编译命令需要添加如下语句:(即将自定义模块的目录加进来)参考如下的 示例: hello handler 模块 部分,重新生成ngnix.exe文件。

qqwangfan的专栏 1171

模型检测--工具KeYmaera

论文:KeYmaera: A Hybrid Theorem Prover for Hybrid Systems 作者:Andre Platzer and JanKeYmaera摘要1 介绍2用于混合系统的KeYmaera验证工具3混合系统,混合自动机和混合程序 摘要 KeYmaera是一种用于混合系统的混合验证工具,它结合了演绎,实数代数和计算机代数证明者技术。它是自然的自动和交互式定理证明器 混合系统的规范和验证逻辑。 KeYmaera支持差分动态逻辑,它是用于混合程序的实值一阶动态逻辑,是混合自动机的程

ziigea的博客 1077

逆向分析-SeparationPreview.aip-分色预览-结构分析(一)-x64dbg条件日志打印-命令表达式-PS脚本

从功能上分析,仅显示使用的专色这个功能,并没有触发插件接口。使用X64dbg加载illustrator进程,切换到句柄窗口,在窗口过程中,右键刷新获取界面。在x64dbg中,在UI中可以输入一些条件表达式,能够计算出对应的值,并打印在日志中。常用的,如果非暂停,输出第一个参数。参数二是utf16的指针,utf16@字符串地址,这里的字符串地址为[[ebp-108]]参数一是utf8的,utf8@字符串地址,这里的字符串地址为[ebp-28]从界面上分析,一个颜色列表,及仅显示专色的多选框组成。

插件开发 644

Nginx 自定义编译与模块添加

已学会了如何重新编译Nginx并添加自定义模块。这不仅提升了您的服务器性能,也增加了其功能性。重新编译Nginx是高级系统管理的一部分,需要对Nginx及其模块有深入的理解。

峰迹的博客 1169

《RT-Thread入门与实战》第1章:RT-Thread概述与核心优势

2006年由熊谱翔发起2017年成立上海睿赛德电子科技公司2021年成为国内首个通过ISO 26262 ASIL-D认证的RTOS。

2301_79143213的博客 985

Nginx源码分析(25篇)

1、Nginx源码分析 - 初探Nginx的架构(01) 2、Nginx源码分析 - 基础数据结构篇 - 内存池 ngx_palloc.c(02) 3、Nginx源码分析 - 基础数据结构篇 - 数组结构 ngx_array.c(03) 4、Nginx源码分析 - 基础数据结构篇 - 缓冲区结构 ngx_buf.c(04) 5、Nginx源码分析 - 基础数据结构篇 - 双向链表结构 ngx_queue.c(05) 6、Nginx源码分析 - 基础数据结构篇 - 单向链表结构 ngx_list.c(06)

xiaohuozi2015的博客 5029

SAP B1中文培訓教材_SDK

公司内部培训资料,对开发工具 ,DIAPI, UIAPI,Add-ON有详细解说

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

深入理解nginx realip模块[上]

本文通过源码分析来详细阐述了nginx的realip 模块的实现原理。

一个致力于开源代码学习、分析和交流的博客 1798

Devexpress16.2.6破解工具

Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具Devexpress16.2.6破解工具

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_core_module

模块的基本属性&ngx_core_module_ctx, /* 模块上下文 */ngx_core_commands, /* 模块支持的配置指令 */NGX_CORE_MODULE, /* 模块类型 */NULL, /* init_master 回调 */NULL, /* init_module 回调 */NULL, /* init_process 回调 */NULL, /* init_thread 回调 */NULL, /* exit_thread 回调 */

weixin_41812346的博客 733

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_cycle_modules

NGX_OK+1。

weixin_41812346的博客 1240

Linux环境,nginx-1.24.0 源码分析

在。

weixin_41812346的博客 634

Ubuntu 下 nginx-1.24.0 源码分析 (1)

environ[i];

weixin_41812346的博客 1269

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_add_inherited_sockets函数

声明在 src\core\nginx.c实现在 src\core\nginx.cngx_int_tNGX_OKNGX_ERRORcycleNGINX_VARNGX_OKfd。

weixin_41812346的博客 841

Ubuntu 下 nginx-1.24.0 源码分析 - conf_ctx

/ 其他字段...// 其他字段...# 工作进程数# 全局错误日志层级 2:HTTP 块(http)作用server {listen 80;# 监听端口# 域名# 站点根目录层级 4:路径(location)作用# 反向代理到后端服务# 代理缓冲区大小继承关系。

weixin_41812346的博客 888

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_show_version_info函数

是 OpenSSL 中的一个宏,用于设置 TLS 扩展中的 Server Name Indication (SNI) 主机名。是 OpenSSL 库中定义的一个宏,用于获取 OpenSSL 的完整描述性版本文本,包括版本号和发布日期。这行代码的意思是:如果用户需要查看配置信息(-V),就执行下面的代码块。这段代码的作用是显示 Nginx 的版本信,帮助信息和编译配置。是一个变量,如果用户请求帮助信息,这个变量会被设置为真。这行代码的意思是:如果用户需要帮助信息,就执行下面的代码块。

weixin_41812346的博客 1072

Ubuntu 下 nginx-1.24.0 源码分析 - ngx_time_init 函数

在 src\core\ngx_times.h。

weixin_41812346的博客 1127
上一篇: Nginx源码分析 - HTTP模块篇 - HTTP模块的阶段处理PHASE handler(23)
下一篇: Nginx源码分析 - 实战篇 - 编写一个阶段化的模块(25)
老码农zhuli
老码农zhuli 领域专家: 后端开发技术领域 领域专家: 后端开发技术领域
博客等级 码龄14年 2456粉丝 312原创
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值