加入收藏 | 设为首页 | 会员中心 | 我要投稿 甘南站长网 (https://www.0941zz.com/)- 科技、行业物联网、开发、云计算、云管理!
当前位置: 首页 > 运营中心 > Nginx > 正文

剖析nginx 客户端返回499的错误码的问题

发布时间:2023-02-20 10:27:55 所属栏目:Nginx 来源:互联网
导读:我们服务架构和错误码是上面这样的,上游服务日志没有记录,无法确定kong到上游服务的连接和请求细节。 kong上的日志 rsp_cost:0.041 rsp_length:0 rsp_status:499 ups_rsp_cost:- ups_rsp_length:0 ups_rsp_status:- waf上的日志 rsp_cost:1.045 rsp_length

  我们服务架构和错误码是上面这样的,上游服务日志没有记录,无法确定kong到上游服务的连接和请求细节。
 
  kong上的日志
  rsp_cost:0.041
  rsp_length:0
  rsp_status:499
  ups_rsp_cost:-
  ups_rsp_length:0
  ups_rsp_status:-
 
  waf上的日志
  rsp_cost:1.045
  rsp_length:0
  rsp_status:499
  ups_rsp_cost:-
  ups_rsp_length:0
  ups_rsp_status:-
  看日志,两个负载均衡的现象一毛一样,kong upstream到web服务上,不太确定是upstream 链接的问题或者是读写数据的问题,或者是kong自己的问题,根本就没有反向代理到上游服务
 
 
  上游服务抓包
  打算在上游服务上抓一下包,看看请求是在kong上出问题了,根本没到上游服务,还是说已经到了上游服务,上游服务出问题了。
 
 
 
  83是kong的ip,82是上游服务的ip
  可以看到,83首先发了fin包,表示要断开连接,之后82也回复了fin的ack包,之后82还在发送数据包,过了大概0.18秒,82才给83发了fin ack包,表示可以断开连接了。这时候由于83早就断开了连接,在这个中间的包,83回复了RST,我们使用的是长链接,83断开连接之后,新的连接已经复用这个TCP连接了,这时候83只能回复RST。大概过程就是这样的。
 
  kong为什么要断开连接?
  由于我们使用upstream是长链接,猜测了很多种可能
 
  keepalive_requests 超过keepalive_requests个请求后就会关闭长链接
  keepalive_time 超过keepalive_time时间后就会关闭长链接
  keepalive_timeout 打开上游服务的超时时间,连接超过keepalive_timeout就认为上游服务已经不可用了,这个参数就直接排除了,抓包已经看到请求已经到了上游服务
  最后都放弃了这个配置,觉得Nginx应该会处理完请求之后再受到keepalive_requests keepalive_time的限制关闭连接,不可能请求处理一半然后直接主动关闭连接,还有一个原因,我们的Nginx版本是1.13,也没有这些配置可以修改。
 
 
  负载均衡的问题?
  最后怀疑是waf上的问题,waf上请求量太大,没去waf机器上抓包,猜测waf抓包跟kong的结果是一样的,然后向前推测waf为什么要断开连接,猜测是不是客户端断开了连接,如果是客户端断开连接的话,所有的看到的日志现象就是通的。
  为了验证这个猜测,我们在测试环境模拟了一下客户端主动断开连接的操作。
  我们先在的上游服务上模拟了一个耗时的请求,然后再没有返回结果的时候主动断开请求。
 

  class TestController extends BaseController
  {
      public function actionTest()
      {
          sleep(3);
          return $this->response->success(array("test","geekbang","es"));
      }
  }
  然后我们在终端上使用curl请求接口,在三秒之内取消请求。
  curl https://test.com/test/test/testctrl+C 取消请求
  然后观察waf的日志,以及kong的日志,跟生产出现的499错误码表现是一样的。
  基本上确定是客户端主动断开连接引起的。
 
 
  修改配置 Nginx的配置
  看一下proxy_ignore_client_abort说明
 
  Syntax: proxy_ignore_client_abort on | off;
  Default:    
  proxy_ignore_client_abort off;
  Determines whether the connection with a proxied server should be closed when a client closes the connection without waiting for a response.
  确定当客户端在不等待响应的情况下关闭连接时,是否应该关闭与代理服务器的连接。
  客户端不等待响应关闭连接时,默认会关闭与代理服务器的连接,改为on就是代理服务器不关闭,直到代理服务器处理完请求。
  在kong上修改配置
  proxy_ignore_client_abort on
  改了一台机器,观察了一天,确定了是因为这个配置,后面把两台机器都改了之后就没有再出现499的错误码。修改了这个配置之后,尽管错误码消失了,但是无效的请求会增加上游服务的压力,本来这个请求已经无意义被客户端关闭了,然后上游服务也被关闭了。打开之后,上游服务不会被关闭,直到请求处理完毕,有利有弊,需要权衡和取舍。

(编辑:甘南站长网)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读