前言

今天测试和我分别压测了HTTP接口,他使用的是测试专用的8核16G压测服务器,所装系统是Windows,我使用的是开发机2核4G,运行环境是 CentOS,走内网压测不存在网络瓶颈,使用相同的测试计划,我压测出来的结果并发数是他的3倍,并且他的测试结果伴有1.7%错误,查看错误发现并不是接口返回,而是Jmeter报出来的。查了一波资料,发现 Windows 环境下的端口循环回收需要消耗2~4分钟。由此猜测可能是由于 Windows 下压测端口数有限,端口资源被占满,没有及时循环回收,导致压测结果不准和报错。

扩大端口数量

因为Windows最大能支持 65534个端口。尝试将端口资源数设置为最大。

  1. 使用 win + R 打开cmd, 输入 regedit 命令打开注册表
  2. 找到 HKEY_LOCAL_MACHINESYSTEMCurrentControlSetServicesTcpipParameters 目录
  3. 右击 Parameters ,添加一个新的 DWORD 命名为 MaxUserPort
  4. 然后双击 MaxUserPort ,输入65534,基数选择十进制(如果是分布式运行的话,控制机器和负载机器都需要这样操作)
  5. 重启使配置项生效

提高端口使用率

采用上述解决方案后,暂时解决了端口占用的问题。在此基础上,将压测的并发数据提高了两倍,但是当短时间请求数量超过65534 端口数时,再次出现了报错。又是一波海量搜索,定位到两个影响端口使用率的主要因素:Time_Wait 和 CLOSE_WAIT ,它们导致端口无法使用。话不多说,弄它。

Time_Wait

Time_Wait解决方案

主要就是通过缩短 Time_Wait 的等待时间,来提高端口的使用效率。

  1. 使用 win + R 打开cmd, 输入 regedit 命令打开注册表
  2. 找到 HKEY_LOCAL_MACHINESYSTEMCurrentControlSetServicesTcpipParameters 目录
  3. 右击 parameters,添加一个新的 DWORD ,命名为 TcpTimedWaitDelay,将值设置为30, 缩短 TIME_WAIT 的等待时间
  4. 重启使配置项生效

CLOSE_WAIT

CLOSE_WAIT 引发问题

Close_Wait 会占用一个连接,网络可用连接小。当数量过多时,可能会引起网络性能下降,并占用系统非换页内存。尤其是在有连接池的情况下(比如 HttpRequest ),会耗尽连接池的网络连接数,导致无法建立网络连接。

CLOSE_WAIT产生原因

  • 一般情况下是因为 TCP 连接没有调用关闭方法,需要应用来处理网络链接关闭
  • 如果是Web请求,经常是因为 Response 的 BodyStream 没有调用 Close。举个例子,Widnows 下使用 HttpWebRequest 一定要保证 GetRequestStream 和 GetResponse 对象关闭,否则容易造成连接处于 CLOSE_WAIT 状态
  • TCP的 KeepLive 功能, 操作系统 默认 7200秒 (2小时) 自动清理一次 CLOSE_WAIT 的连接,满足不了高并发下的端口需求数。支持自定义配置

CLOSE_WAIT解决方案

  1. 使用 win + R 打开cmd, 输入 regedit 命令打开注册表
  2. 找到HKEY_LOCAL_MACHINESYSTEMCurrentControlSetServicesTcpipParameters目录
  3. 在该目录下添加新的配置项。设置合理的 Keepalive 参数
    "KeepAliveTime"=dword:006ddd00
    "KeepAliveInterval"=dword:000003e8
    "MaxDataRetries"="5"
  4. 重启使配置项生效

总结

至此,Windows下使用 Jmeter 压测 出现的”ADDRESS ALREADY IN USE: CONNECT“的问题得以解决,要记住解决问题的两个关键点哟:

  1. 扩大端口数量
  2. 提高端口使用率
最后修改:2020 年 03 月 04 日 01 : 09 PM
如果觉得我的文章对你有用,请随意赞赏