NGINX+NJS应用场景之 PASV模式下FTP ALG协议支持
2020-04-13 13:58:45
宗兆伟
NJS旨在成为NGINX的通用脚本框架。
NJS允许用户用脚本的方式给复杂业务场景下的流量负载添加处理逻辑。
它是扩展NGINX 应用的一把利刃。
编者注:
文本所涉及源码均可通过访问以下github 代码仓库获得。
https://github.com/zongzw-nginx/nginx-njs-usecases
一、关于FTP ALG
关于FTP ALG 的相关概念可以从以下链接查阅:
https://www.juniper.net/documentation/en_US/junos/topics/topic-map/security-ftp-alg.html
在FTP 被动(PASSIVE)传输模式中:
PASV命令请求服务器侦听一个端口,这个端口不是服务器默认数据端口,而是服务器自定的一个端口。服务器开启此端口后等待连接。对PASV命令的响应包括服务器的主机和监听端口地址。
对于FTP 服务器在内网的情况,被动模式下,FTP 服务器告知客户端等待连接的主机和端口信息,不能是本机信息,而应该是网络边界上客户端可以连接到的端口信息。否则客户端就不能主动连接FTP服务器的数据端口。
但是很多情况下FTP服务器并不知道边界网关的信息。这时就会用到ALG(Application Layer Gateway),在FTP服务器给出PASV命令响应后,由边界路由器修改此响应中的主机和端口信息。以便让客户端顺利的连接到网关,网关负责再将数据传输转给后端FTP服务器。
大多数的路由协议中都支持ALG协议。所以FTP服务器可以以被动模式运行在网络内部。
二、NGINX + NJS 实现
1.部署及设计
本文给大家展示的是如何使用NGINX 和NJS 实现 ALG协议简单支持,即FTP服务器不可见,由NGINX代理FTP服务器的控制和数据链路。
下图是示例的部署环境,可以看出。
FTP服务器运行在Docker Cluster内部,运行于被动模式,并不暴露任何端口供外界连接,只是让Docker Cluster内的其他container访问21 和20000。前面通过NGINX做反向代理。用户可以访问它的8101端口进行数据链路控制,也可以访问8080端口做数据传输。
在被动模式下MYFTP告诉FTP客户端去连接127. 0.0.1:20000,但是这个连接显然是不能建立的。NGINX完成对PASV指令的响应的修改。报文中127.0. 0.1:20000被改成了172.100.0.106:8080。如下图所示:
之后的传输中FTP客户端去连接NGINX,NGINX负责把数据传输代理到后端的FTP服务器。
数据传输效果,如下图所示:
2.NJS实现
a)我们先看下NGINX 配置文件:
配置部分较为简单,我们监听了两个端口21, 和8080, 分别用于控制流和数据流传输。
控制流中我们使用ftp_controller 对数据流中的PASV响应做处理。
数据流中我们将数据代理到上游,上游的端口使用js_set来决定。这里是把端口20000参数化了。
“ proxy_download_rate 1k;”是为了演示多连接同时存在情况下的异常报错。
b)再看下NJS代码实现部分:
在 ftp_controller中,我们注册一个上行过滤函数:
“s.on('upload', function(data, flags){”
该函数会检查从客户端过来的数据包内容,如果发现有PASV指令,则会注册一个下行过滤函数:
“s.on('download', handle_pasv);”
这个函数会检查从服务器端传给客户端的数据流,根据FTP控制协议,PASV指令的响应格式为:“/227 .*\(.*\)/”
。
如果发现由此内容,就将括号中的内容替换成NGINX的地址和端口。
“function get_pasv_conn(s, ipaddr, port)”负责生成连接信息字符串。
注意在处理完毕后及时调用s.off 可以减少NJS对数据流的无用处理消耗。
至此,我们就可以实时监控并修改控制流中的PASV指令及响应,同时监听并代理数据流。
总结:
NJS ngx_stream_js_module 提供给我们对流操作的能力,通过s.on s.off 可以挂载对数据流的处理钩子。
修改后,数据流TCP层的校验等不需要我们去考虑,NGINX帮我们完成。
发布评论 加入社群
相关文章

博文精选 | 对话中国移动:支撑数亿用户的基础设施如何实施云原生改造?
F5小安
2021-12-27 10:58:54 381

博文精选 | 对话中国移动:支撑数亿用户的基础设施如何实施云原生改造?
F5小安
2021-12-27 10:58:53 406

NJS应用实例之 日志内容脱敏
宗兆伟
2020-04-10 11:32:55 1246

回复评论
发布评论