背景
为某SaaS平台的数据推送服务写的接口无法及时响应数据推送请求,导致频繁出现因请求超时而导致的数据推送失败,进而严重影响业务使用。接口部署在公司的阿里云上。
故障点梳理
根据以上的网络拓扑图,可以初步考虑故障点范围:
- 远端服务器
- 公司防火墙
- 公司服务器
- 容器
- 应用程序
由于容器仅是对服务器网络的桥接,并未进行特殊配置,所以故障点5应最先被排除。
测试环境
疑似故障服务器:47.xx.xx.xx(公司阿里云)
测试服务器:39.xx.xx.xx(公司阿里云)、61.xx.xx.xx(非公司服务器)
2021-08-25
查看平台后台日志发现失败原因全部为推送超时,如下图所示。
查看接口服务器日志显示24日晚10点到25日早10点内,所有接收到的请求均正常处理且正常响应。
使用平台提供的连接测试工具对47.xx.xx.xx服务器进行连接测试,出现偶发性响应超时。
使用61.xx.xx.xx和39.xx.xx.xx两台服务器进行对比测试,其中61.xx.xx.xx为联通专线网络,39.xx.xx.xx与47.xx.xx.xx网络环境一致。在61与39服务器上部署相同版本的接口后,再使用平台测试工具进行测试后发现,39亦出现与47相同的响应超时问题,而61则正常。
通过与平台客服沟通后确认,并不存在对某些IP限制推送的可能,所以故障点1被排除;随后进行如下尝试:
- 暂时关闭39、47服务器的云盾;# 2021-08-26
- 检查远端服务器IP是否在被限制名单内
但问题依然存在,需进一步分析故障点2、3、5
2021-08-26
通过测试发现,对于一切正常的服务器61,所有请求均可正常到达应用程序且应用程序处理后正常返回,如下图所示:
而在47与39服务器上,相同代码的应用程序无法接收到请求导致请求超时。
进一步,使用netcat工具,模拟应用程序接收并响应请求
>>> while true; do echo -e "HTTP/1.1 200 OK\n" | nc -l -p 3120 -w 1; done
发现服务器61一切正常,39与47仍无法接收请求
综上,可以排除故障点5的问题。
目前仅剩故障点2和3
通过在防火墙与服务器上同时进行网络抓包
>>> tcpdump -i eth0 -A -s 0 'tcp port 3120' -w dump.cap
从抓包结果可以看到防火墙与服务器上都出现“在成功握手若干次后服务器对远端服务器的握手请求无返回”的现象。即无法建立TCP连接,导致远端服务器请求无法发送。故能够排除故障点2的问题,所以只可能是故障点3,即服务器的问题。
将抓包文件交由阿里云专家处理
2021-08-27
最终确认是由于前期进行接口压测而修改了39与47服务器的参数:
# /etc/sysctl.conf
net.ipv4.tcp_tw_recycle=1
将其改为0,恢复正常。
# /etc/sysctl.conf
net.ipv4.tcp_tw_recycle=0
# sysctl -p
注:tcp_tw_recycle参数在系统内核版本4.12后被移除
参考:
- https://www.cnxct.com/coping-with-the-tcp-time_wait-state-on-busy-linux-servers-in-chinese-and-dont-enable-tcp_tw_recycle/
- http://blog.itpub.net/31559359/viewspace-2284113/
- https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/commit/?id=4396e46187ca5070219b81773c4e65088dac50cc
总结
- 网络及服务器的小白切勿设置tcp_tw_recycle参数为1,因为你遇到的问题级别还达不到需要设置它的程度;
- 这篇博客害人不浅https://blog.csdn.net/apple9005/article/details/82556794
这篇博客和我遇到的问题一样,分析也比我专业,可以参考一下:
https://blog.csdn.net/sz85850597/article/details/107580686?utm_medium=distribute.pc_relevant.none-task-blog-2defaultbaidujs_title~default-0.control&spm=1001.2101.3001.4242