当前位置: 首页 > news >正文

nginx upstream server主动健康检测模块添加https检测功能[完整版]

目录

  • 1 缘起
    • 1.1 功能定义
  • 2. 实现后的效果
  • 2.1 配置文件
  • 2.2 运行效果
  • 3. 代码实现
    • 3.1 配置指令
      • 3.1.1 配置指令定义:
      • 3.1.2 配置指令结构体:
      • 3.1.3 配置指令源码定义:
    • 3.2 模块的初始化
    • 3.3 添加新的健康检测类型的定义
    • 3.4 握手完成后的处理
    • 3. 5 发送http请求
    • 3.6 接收http响应
    • 3.7 连接关闭
    • 3.8 ssl上下文的释放

1 缘起

  前面的《nginx upstream server主动健康检测模块ngx_http_upstream_check_module 使用和源码分析》系列已经分析了ngx_http_upstream_check_module的实现原理,并且在借助这个模块的框架实现了一个udp健康检测的新功能。
  但是ngx_http_upstream_check_module还缺乏基于https监测上游服务器健康状况的能力,始终是一个缺憾,因此,本文基于《nginx upstream server主动健康检测模块ngx_http_upstream_check_module 使用和源码分析》和《nginx stream proxy 模块的ssl连接源码分析》两篇博文的分析成果,来实现一个基于https的上游服务器健康检测的能力。

1.1 功能定义

  本次支持的功能:

  • 支持向上游服务器发起https请求功能
  • 请求的报文复用原有的http检测的请求报文定义
  • 响应的状态码检测复用原有的http检测的响应码的定义
  • 支持ssl握手过程中添加sni扩展信息
  • 支持ssl握手协议类型的配置
  • 支持ssl握手协议加密套件的配置

  暂时不支持的功能:

  • 不支持ssl会话复用(会话复用可以降低上游服务器的ssl握手压力)
  • 不支持ssl证书双向验证
  • 不支持服务器端证书有效性验证

&ems;  由于本次主要是检验https的链接握手流程,对一些不是特别关键的ssl握手特性暂时不支持主要是为了简化代码逻辑,但是不影响业务流程,这样也便于在本文中将整个实现流程进行阐述。后续可以参照ngx_stream_proxy_module中的实现,继续将这些特性进行完善,以臻于完美。

2. 实现后的效果

  首先来看一下实现后的效果,有一些感性的认识。

2.1 配置文件


#user  nobody;
worker_processes  1;
daemon off;
master_process off;error_log  logs/error.log;
pid        logs/nginx.pid;load_module  objs/ngx_http_upstream_check_module.so;events {worker_connections  1024;
}http {include       mime.types;default_type  application/octet-stream;log_format  main  '$remote_addr - $remote_user [$time_local] "$request" ''$status $body_bytes_sent "$http_referer" ''"$http_user_agent" "$http_x_forwarded_for"';access_log  logs/access.log  main;sendfile        on;keepalive_timeout  65;upstream backend {# 开启https健康检测check type=https interval=3000 rise=2 fall=5 timeout=1000 port=443;check_http_send "GET / HTTP/1.1\r\nHost: www.baidu.com\r\n\r\n";check_http_expect_alive http_2xx http_3xx;# 设置sni hostnamecheck_ssl_server_name www.baidu.com;server 183.240.99.24:443;}server {listen       9080;server_name  localhost;# 开启本模块的状态查询接口	location /status {check_status html;}location / {proxy_pass http://backend;}#error_page  404              /404.html;# redirect server error pages to the static page /50x.html#error_page   500 502 503 504  /50x.html;location = /50x.html {root   html;}}
}

   这里假设将www.baidu.com作为被代理的上游服务器,以上配置文件中的upstream块中定义了一个https的健康检测类型, check_http_send复用了http的定义,而check_ssl_server_name是新增的指令,用来配置ssl握手设置sni扩展信息中的主机host信息。

2.2 运行效果

  启动tengine后,可以通过查看nginx的error.log日志进行观察, 可以看到如下信息:

2024/02/16 09:31:33 [error] 23638#0: https check failed with return code: 403
2024/02/16 09:31:33 [error] 23638#0: check protocol https error with peer: 192.168.0.1:443
2024/02/16 09:31:45 [info] 23663#0: enable check peer: 192.168.0.1:443

error.log中的前面两条因为服务器响应403报了错误,对应在配置了“check_http_expect_alive http_2xx http_3xx;”的情况。如果配置改成“check_http_expect_alive http_2xx http_3xx http_4xx;” 则报后面那条上游服务器enable的信息。证明https的检测功能已经可用了。
  另外我们可以通过wireshark抓包观察交互的情况,抓包如下:
在这里插入图片描述

  从上述抓包的内容可以看到ssl的握手交互的过程都已经有了。关于如何进行ssl握手的内容不在本文的讨论范围之内,可以参考HTTPS篇之SSL握手过程详解 或者通过Wireshark分析HTTPS握手过程与协议概述

3. 代码实现

  由于https进行ssl握手,需要一些额外的参数,因此在nginx的配置文件http.upstream块中需要新增一些配置指定定义。

3.1 配置指令

3.1.1 配置指令定义:

支持的配置指令如下:

  • check_ssl_ciphers:
        配置加密套件,格式参考proxy_ssl_ciphers
  • check_ssl_protocols:
        和服务器交互采用的ssl协议版本,如TLSv1.1 TLSv1.2等,格式参考proxy_ssl_protocols。
  • check_ssl_server_name:
        和服务器进行ssl握手时候采用的sni扩展host名字,如果不设置并且upstream块中的server是用域名设置的,那么默认就采用设置的服务器名字。
  • check_ssl_verify:[on/off]
        是否校验服务器的证书有效性。(待后续实现)
  • check_ssl_session_reuse: [on/off]
        和上游服务器进行ssl握手的时候是否复用ssl会话信息。(待后续实现)

3.1.2 配置指令结构体:

   为了对上述定义的配置指令进行保存,需要在ngx_http_upstream_check_srv_conf_s结构体中增加对应的参数,包括ssl_ciphers、ssl_protocols、ssl_server_name和ssl四个参数,其中ssl参数用来保存ssl协议配置上下文。


struct ngx_http_upstream_check_srv_conf_s {ngx_uint_t                               port;ngx_uint_t                               fall_count;ngx_uint_t                               rise_count;ngx_msec_t                               check_interval;ngx_msec_t                               check_timeout;ngx_uint_t                               check_keepalive_requests;ngx_check_conf_t                        *check_type_conf;ngx_str_t                                send;union {ngx_uint_t                           return_code;ngx_uint_t                           status_alive;} code;ngx_array_t                             *fastcgi_params;ngx_uint_t                               default_down;ngx_uint_t                               unique;ngx_uint_t                               udp : 1;                       /* 是否udp socket */ngx_int_t                                match_part : 1;                /* 是否只要部分匹配就可以了 */ngx_int_t                                match_offset;                  /* udp响应期望的内容从哪个字节开始匹配 */ngx_str_t                                expect;                        /* udp响应的期望内容 */#if (NGX_HTTP_SSL)ngx_ssl_t                               *ssl;                            /* ssl 配置上下文 */ngx_str_t                                ssl_ciphers;                    /* ssl 加密套件 */ngx_uint_t                               ssl_protocols;                  /* 采用的ssl协议 */ngx_str_t                                ssl_server_name;                /* ssl握手的sni扩展hostname */
#endif
};

  以上添加的ssl_protocols参数在ngx_http_upstream_check_create_srv_conf函数中需要将其设置为NGX_CONF_UNSET_UINT,避免nginx在解析配置文件的时候出现参数重复的报错。

3.1.3 配置指令源码定义:

#if (NGX_HTTP_SSL){ ngx_string("check_ssl_ciphers"),NGX_HTTP_UPS_CONF|NGX_CONF_TAKE1,ngx_conf_set_str_slot,NGX_HTTP_SRV_CONF_OFFSET,offsetof(ngx_http_upstream_check_srv_conf_t, ssl_ciphers),NULL },{ ngx_string("check_ssl_protocols"),NGX_HTTP_UPS_CONF|NGX_CONF_1MORE,ngx_conf_set_bitmask_slot,NGX_HTTP_SRV_CONF_OFFSET,offsetof(ngx_http_upstream_check_srv_conf_t, ssl_protocols),&ngx_upstream_check_ssl_protocols },{ ngx_string("check_ssl_server_name"),NGX_HTTP_UPS_CONF|NGX_CONF_FLAG,ngx_conf_set_str_slot,NGX_HTTP_SRV_CONF_OFFSET,offsetof(ngx_http_upstream_check_srv_conf_t

相关文章:

nginx upstream server主动健康检测模块添加https检测功能[完整版]

目录 1 缘起1.1 功能定义2. 实现后的效果2.1 配置文件2.2 运行效果3. 代码实现3.1 配置指令3.1.1 配置指令定义:3.1.2 配置指令结构体:3.1.3 配置指令源码定义:3.2 模块的初始化3.3 添加新的健康检测类型的定义3.4 握手完成后的处理3. 5 发送http请求3.6 接收http响应3.7 连…...

django中admin页面汉化

在Django中,将admin界面汉化为中文需要进行一些配置和翻译文件的添加。下面是一个基本的步骤指南,帮助你实现Django admin的汉化: 一:安装并配置Django: 如果你还没有安装Django,首先通过pip安装它: pip…...

prometheus基于consul的服务发现

文章目录 一、基础二、安装consul下载地址启动consul访问consul 三、编写服务发现文件nodes.json四、prometheus配置consul发现修改prometheus.yml重启Prometheus 参考 一、基础 二、安装consul 下载地址 https://developer.hashicorp.com/consul/install 启动consul mkdi…...

深度学习之pytorch实现线性回归

度学习之pytorch实现线性回归 pytorch用到的函数torch.nn.Linearn()函数torch.nn.MSELoss()函数torch.optim.SGD() 代码实现结果分析 pytorch用到的函数 torch.nn.Linearn()函数 torch.nn.Linear(in_features, # 输入的神经元个数out_features, # 输出神经元个数biasTrue # 是…...

Vue3快速上手(八) toRefs和toRef的用法

顾名思义&#xff0c;toRef 就是将其转换为ref的一种实现。详细请看&#xff1a; 一、toRef 1.1 示例 <script langts setup name"toRefsAndtoRef"> // 引入reactive,toRef import { reactive, toRef } from vue // reactive包裹的数据即为响应式对象 let p…...

《数学建模》专栏导读

文章分类 相关概念入门快速建模相关混合整数线性规划&#xff08;MILP&#xff09;加速技巧数值问题探讨相关问题解决技巧 相关概念入门 文章相关概念离散优化模型的松弛模型线性松弛问题混合整数线性规划MILP问题中增添约束的影响约束的影响 快速建模相关 文章求解器涉及步…...

App启动优化笔记 1

app大致的启动流程。有Launcher进程,system_server进程,zygote进程,APP进程。 Launcher进程:启动activity来启动应用 system_server进程:(ams是其中的一个binder):发送一个socket消息给Zygote。 zygote进程:收到消息后,fork新的进程,---》app进程启动 APP进程:…...

Spring Boot 笔记 027 添加文章分类

1.1.1 添加分类 <!-- 添加分类弹窗 --> <el-dialog v-model"dialogVisible" title"添加弹层" width"30%"><el-form :model"categoryModel" :rules"rules" label-width"100px" style"padding…...

【SQL】sql记录

1、start with star with 是一种用于层次结构查询的语法&#xff0c;它允许我们从指定的起始节点开始&#xff0c;递归查询与该节点相关联的所有子节点。 SELECT id, name, parent_id from test001 START WITH id 1 CONNECT BY PRIOR id parent_id 2、row_number() over pa…...

嵌入式培训机构四个月实训课程笔记(完整版)-Linux ARM驱动编程第六天-ARM Linux编程之SMP系统 (物联技术666)

链接&#xff1a;https://pan.baidu.com/s/1V0E9IHSoLbpiWJsncmFgdA?pwd1688 提取码&#xff1a;1688 SMP&#xff08;Symmetric Multi-Processing&#xff09;&#xff0c;对称多处理结构的简称&#xff0c;是指在一个计算机上汇集了一组处理器(多CPU),各CPU之间共享内存子系…...

html5播放 m3u8

注意&#xff1a;m3u8地址要为网络地址&#xff0c;直接把代码复制为html直接在本地打开&#xff0c;可能不行&#xff0c;需要放在nginx或者apache或者其他的web服务器上运行。 <!DOCTYPE html> <html> <head><meta charsetutf-8 /><title>测试…...

微信小程序按需注入和用时注入

官网链接 按需注入 {"lazyCodeLoading": "requiredComponents" }注意事项 启用按需注入后&#xff0c;小程序仅注入当前访问页面所需的自定义组件和页面代码。未访问的页面、当前页面未声明的自定义组件不会被加载和初始化&#xff0c;对应代码文件将不…...

iPhone 16 组件泄露 揭示了新的相机设计

iPhone 16 的发布似乎已经等了很长一段时间&#xff0c;但下一个苹果旗舰系列可能会在短短 7 个月内与我们见面——而新的组件泄漏让我们对可能即将到来的重新设计有了一些了解。后置摄像头模块。 爆料者 Majin Bu&#xff08;来自 MacRumors&#xff09;获得的示意图显示&…...

网络工程师学习笔记——IPV6

20世纪80年代&#xff0c;IETF&#xff08;Internet Engineering Task Force&#xff0c;因特网工程任务组&#xff09;发布RFC791&#xff0c;即IPv4协议&#xff0c;标志IPv4正式标准化。在此后的几十年间&#xff0c;IPv4协议成为最主流的协议之一。无数人在IPv4的基础上开发…...

【零基础学习CAPL】——CAN报文的发送(LiveCounter——生命信号)

🙋‍♂️【零基础学习CAPL】系列💁‍♂️点击跳转 文章目录 1.概述2.面板创建3.系统变量创建4.CAPL实现5.效果5.1.0~15循环发送5.2.固定值发送6.全量脚本1.概述 本章主要介绍带有生命信号LiveCounter的报文发送脚本 一般报文可使用CANoe的IG模块直接发送,但存在循环冗余…...

git提交代码冲突

用idea2023中的git提交代码&#xff0c;出现 error: Your local changes to the following files would be overwritten by merge: ****/****/****/init.lua Please commit your changes or stash them before you merge. Aborting 出现这个错误可能是因为你的本地修改与远…...

树莓派:使用mdadm为重要数据做RAID 1保护

树莓派作为个人服务器可玩性还是有点的。说到服务器&#xff0c;在企业的生成环境中为了保护数据&#xff0c;基本上都会用到RAID技术。比如&#xff0c;服务器两块小容量但高性能的盘做个RAID-1按装操作系统&#xff0c;余下的大容量中性能磁盘做个RAID-5或者RAID-6存放数据。…...

HTML板块左右排列布局——左侧 DIV 固定宽度,右侧 DIV 自适应宽度,填充满剩余页面

我们可以借助CSS中的 float 属性来实现。 实例&#xff1a; 布局需求&#xff1a; 左侧 DIV 固定宽度&#xff0c;右侧 DIV 自适应宽度&#xff0c;填充满剩余页面。 <!DOCTYPE html> <html><head><meta charset"UTF-8"><meta http-e…...

红旗linux安装32bit依赖库

红旗linux安装32bit依赖库 红旗linux安装32bit依赖库 lib下载 红旗-7.3-lib-32.tar.gz 解压压缩包&#xff0c;根据如下进行操作 1.回退glibc(1)查看当前glibc版本[root192 ~]# rpm -qa | grep glibcglibc-common-2.17-157.axs7.1.x86_64glibc-headers-2.17-260.axs7.5.x86_…...

Stable Diffusion教程——使用TensorRT GPU加速提升Stable Diffusion出图速度

概述 Diffusion 模型在生成图像时最大的瓶颈是速度过慢的问题。为了解决这个问题&#xff0c;Stable Diffusion 采用了多种方式来加速图像生成&#xff0c;使得实时图像生成成为可能。最核心的加速是Stable Diffusion 使用了编码器将图像从原始的 3512512 大小转换为更小的 46…...

(二)TensorRT-LLM | 模型导出(v0.20.0rc3)

0. 概述 上一节 对安装和使用有个基本介绍。根据这个 issue 的描述&#xff0c;后续 TensorRT-LLM 团队可能更专注于更新和维护 pytorch backend。但 tensorrt backend 作为先前一直开发的工作&#xff0c;其中包含了大量可以学习的地方。本文主要看看它导出模型的部分&#x…...

【第二十一章 SDIO接口(SDIO)】

第二十一章 SDIO接口 目录 第二十一章 SDIO接口(SDIO) 1 SDIO 主要功能 2 SDIO 总线拓扑 3 SDIO 功能描述 3.1 SDIO 适配器 3.2 SDIOAHB 接口 4 卡功能描述 4.1 卡识别模式 4.2 卡复位 4.3 操作电压范围确认 4.4 卡识别过程 4.5 写数据块 4.6 读数据块 4.7 数据流…...

srs linux

下载编译运行 git clone https:///ossrs/srs.git ./configure --h265on make 编译完成后即可启动SRS # 启动 ./objs/srs -c conf/srs.conf # 查看日志 tail -n 30 -f ./objs/srs.log 开放端口 默认RTMP接收推流端口是1935&#xff0c;SRS管理页面端口是8080&#xff0c;可…...

BCS 2025|百度副总裁陈洋:智能体在安全领域的应用实践

6月5日&#xff0c;2025全球数字经济大会数字安全主论坛暨北京网络安全大会在国家会议中心隆重开幕。百度副总裁陈洋受邀出席&#xff0c;并作《智能体在安全领域的应用实践》主题演讲&#xff0c;分享了在智能体在安全领域的突破性实践。他指出&#xff0c;百度通过将安全能力…...

在Ubuntu24上采用Wine打开SourceInsight

1. 安装wine sudo apt install wine 2. 安装32位库支持,SourceInsight是32位程序 sudo dpkg --add-architecture i386 sudo apt update sudo apt install wine32:i386 3. 验证安装 wine --version 4. 安装必要的字体和库(解决显示问题) sudo apt install fonts-wqy…...

基于 TAPD 进行项目管理

起因 自己写了个小工具&#xff0c;仓库用的Github。之前在用markdown进行需求管理&#xff0c;现在随着功能的增加&#xff0c;感觉有点难以管理了&#xff0c;所以用TAPD这个工具进行需求、Bug管理。 操作流程 注册 TAPD&#xff0c;需要提供一个企业名新建一个项目&#…...

AGain DB和倍数增益的关系

我在设置一款索尼CMOS芯片时&#xff0c;Again增益0db变化为6DB&#xff0c;画面的变化只有2倍DN的增益&#xff0c;比如10变为20。 这与dB和线性增益的关系以及传感器处理流程有关。以下是具体原因分析&#xff1a; 1. dB与线性增益的换算关系 6dB对应的理论线性增益应为&…...

LINUX 69 FTP 客服管理系统 man 5 /etc/vsftpd/vsftpd.conf

FTP 客服管理系统 实现kefu123登录&#xff0c;不允许匿名访问&#xff0c;kefu只能访问/data/kefu目录&#xff0c;不能查看其他目录 创建账号密码 useradd kefu echo 123|passwd -stdin kefu [rootcode caozx26420]# echo 123|passwd --stdin kefu 更改用户 kefu 的密码…...

JavaScript基础-API 和 Web API

在学习JavaScript的过程中&#xff0c;理解API&#xff08;应用程序接口&#xff09;和Web API的概念及其应用是非常重要的。这些工具极大地扩展了JavaScript的功能&#xff0c;使得开发者能够创建出功能丰富、交互性强的Web应用程序。本文将深入探讨JavaScript中的API与Web AP…...

STM32HAL库USART源代码解析及应用

STM32HAL库USART源代码解析 前言STM32CubeIDE配置串口USART和UART的选择使用模式参数设置GPIO配置DMA配置中断配置硬件流控制使能生成代码解析和使用方法串口初始化__UART_HandleTypeDef结构体浅析HAL库代码实际使用方法使用轮询方式发送使用轮询方式接收使用中断方式发送使用中…...