ShokaX

Tengine动态修改upstream

发布于 字数统计 5.5k 字 阅读时长 19 分钟

Tengine动态修改upstream

发布于 字数统计 5,543 阅读时长 28 分钟

环境搭建

目的

在更新nginx upstream pool时,一般方案是更新nginx配置文件,然后reload nginx, 在nginx繁忙时会导致worker process长久处于shutdowning, 并且频繁的upstram可能导致nginx芭比Q。
所以我们这里需要解决的问题就是怎么不reload就能实现修改nginx配置。
以下环境搭建是基于Ubuntu的。

下载tar包

到官方下载tar包 http://tengine.taobao.org/download.html
这里下载最新的2.3.3

 wget http://tengine.taobao.org/download/tengine-2.2.3.tar.gz

运行环境检测脚本,安装nginx依赖库(pcre、openssl、zlib)

提前安装需要的依赖(也可以先运行configure,根据缺少的逐步安装)

apt-get install gcc -y
apt-get install libpcre3 libpcre3-dev -y
apt-get install openssl libssl-dev -y
apt-get install zlib1g-dev -y

解压tar包后进入目录,运行目录下的configure文件
此时如果系统缺少必要的组件,会报错。我们只需要根据报错信息进行解决即可。(如图,代表缺少gcc)

image-20220321115117721

这里要求gcc,所以我们先安装安装。
安装完毕后再次执行,发现新的报错。

image-20220321115125365

根据报错进行安装,这里是缺少PCRE,再次运行,缺少openssl,继续安装。

image-20220321115129460

此时再次运行,缺少zlib库,再次下载。

image-20220321115136158

最后没有报错了,环境检查没问题。如下图,是安装的默认参数。

这里jemalloc是内存优化的,需要的就装,不需要的就不管。

image-20220321115145803

这里给上jemalloc的安装操作(根据需求决定是否要加),首先下载jemalloc,然后进行解压即可,其他不需要操作,到后面的时候再操

wget https://github.com/jemalloc/jemalloc/releases/download/5.2.1/jemalloc-5.2.1.tar.bz2
tar -jxvf jemalloc-5.2.1.tar.bz2 

安装tengine

到这里正式开始安装。安装完成后,会在/usr/local/nginx下看到tengine的安装文件(默认情况下,如果没设置了configure —prefix=/xx/xx的话)

./configure --prefix=/usr/local/tengine --without-http_upstream_keepalive_module --with-http_stub_status_module --with-http_ssl_module --with-http_v2_module --with-stream --with-http_realip_module --add-module=./modules/ngx_http_upstream_*

PS:如果需要加jemalloc的话,加上参数(后面的是解压的路径) —with-jemalloc=~/jemalloc-5.2.1/

然后就可以编译了,完成后就会在前面我们设置的安装目录下找到服务。

make && make install

image-20220321115330278

这里就其实和nginx一样,只是这里没有注册成服务,所以需要到安装目录下去执行二进制文件,当然我们也可以把他cp到 /usr/local/sbin上就可以了。

/usr/local/nginx/sbin/nginx -V 

image-20220321115504627

/usr/local/nginx/sbin/nginx # 启动nginx,不需要参数

此时访问80端口即可看到如下界面

image-20220321115523250

image-20220321115529245

配置

略,就和nginx一样。

dyups动态更新upstream

为了针对nginx不能动态修改配置文件这一痛点,dyups应运而生,这个模块能够实现动态修改配置。他的原理其实就是相当于把一个配置文件给加到了动态内存中,然后通过web进行管控从而实现动态修改。
PS:因为我在前面build的时候加入了upstream模块,所以直接用就行。

如图,这里就是在8000端口监听了dyups的控制端,然后我们就可以通过访问这个端口从而对内存中的conf文件进行修改了。
下面的配置实现的功能就是一个将流量根据upstream转发的配置

image-20220321120003244

使用allow和deny可以设置这个接口允许访问的ip

image-20220321120047897

那么upstream是什么呢?在配置文件中他长这样,如果我们设置了如下的配置,那么对于上述的转发配置,我们的host如果是hots1,流量就反代到8088端口。如果host是host2,则反代到对应的下面那个端口。

image-20220321120052721

那么我们怎么动态更新这个upstream呢?前面也讲了,dyups通过监听一个端口实现对内存中的一个upstream配置文件修改,因此我们只需要调用这个web接口即可。

GET方法(读)

  • /detail #获取全部upstream的详细信息
  • /list #获取upstream的列表
  • /upstream/ #查询指定upstream的信息

POST方法(写)

  • /upstream/ #修改upstream的信息(如果不存在这个upstream,则增加)

DELETE方法(删除)

  • /upstream/ #删除这个upstream

查看当前upstream的细节。 GET方法

image-20220321121218443

修改指定upstream (如果没这个name,就会增加,有就会修改)

image-20220321121221606

删除指定upstream

image-20220321121224535

效果展示

这里,我们本地docker开启了两个不同的服务,接着我们尝试通过不同的域名来实现访问这两个服务。

image-20220321121401874

这里我们想要的结果是动态修改配置,使得访问 host1则能到达50001,访问host2到达50002 .

因此我们只需要加两个upstream即可。

如图,向dyups管理端发送如下两个数据包即可完成添加upstream。

curl -d "server 127.0.0.1:50001;" 192.168.5.179:8000/upstream/1.aaa.com #对应的curl命令

image-20220321121435172

image-20220321121437943

此时访问1.aaa.com和2.aaa.com即可达成目的。

题外话,使用nginx做隧道

Q:既然nginx是个反代服务器,那么是不是也能够实现其他协议的隧道代理功能呢。

A:nginx本身只是web服务器,在默认情况下是不支持其他协议的反代的。但nginx在1.9.0开始,新增了一个stream模块,可以用来实现其他协议的转发、代理和负载。

查看是否存在stream模块

stream模块默认情况下是不会编译到nginx中的,所以在编译nginx的时候需要带上参数 —with-stream

nginx -V #查看nginx的详细信息,看是否存在stream模块

image-20220321121626858

使用steam进行端口映射(反代)

这里我们选择让nginx反代内网的一个22端口

只需要在nginx配置文件中添加stream键值(和event、http同级)即可。

如下配置的意识是在nginx监听本地3389端口,把这个端口的流量给代理到upstream aaa上,而

aaa的目标又是内网的一个ssh端口

因此这里最终结果就是访问nginx服务器的3389等价于访问内网的ssh了。

image-20220321121647179

使用nginx做socket隧道(正向代理)

A

,那么我们肯定不想止步于此,我们想让nginx在渗透周期中做更多的事情,比如做socket隧道?

Q

,nginx本身不支持,需要第三方模块。但是我找到的两个第三方模块在编译的时候都报错了。只能说结局待定了。

https://github.com/zmkeil/ngx_socks.git