dubbo服务端有返回对象,客户端接收到null的问题【紧急】

Created on 15 Jun 2016  ·  5Comments  ·  Source: apache/dubbo

dubbo服务端有返回,客户端接收到null的问题【紧急】

现象

服务端日志已经显示返回结果,结果为自定义对象
格式如下:

AcctQueryFacadeImpl.acctBalanceQuery00, resp=AcctBalanceQuery00Resp[uid=1355739,acctStatus=N,createTime=Fri Mar 04 21:36:31 CST 2016,updateTime=Wed Apr 20 19:52:24 CST 2016,acctId=4985191,balance=0,frozenBalance=0,withdrawBalance=0,respDesc=成功,respCode=000000], time=2ms

客户端接收到的对象为null

该现象并不是必现,

  • 现象1:调用acctBalanceQuery00方法一天有几十万次,目前出现问题的仅3例
  • 现象2:有2条失败数据,重试之后,1条成功,1条仍然失败
  • 现象3:很多业务调用acctBalanceQuery00方法,但目前只有1个业务出问题,这些业务入参基本一样,(此现象也许是巧合)
  • 现象4:用dubbo telnet invoke acctBalanceQuery00方法,有结果返回,用出问题的数据invoke,也有结果返回,所有机器都试过

补充说明

出现问题时,并发量可能并不高,不超过100,而且并发量最高的业务,并没有出现异常,反而是一个并发并不高的业务请求查询时,出错概率奇高,发生3次批量调用,20笔调用,3笔出现问题
调用关系:该出问题业务模块为C,功能服务为B和A,调用次序是,C->B->A,均是dubbo通信调用。
出问题时,A返回结果,B拿到null,B封装一个结构返回至C,C拿到null。
请求响应没有超时。

环境

  • jdk1.8
  • dubbo版本 2.5.5
  • 服务端4台,客户端10台左右

dubbo服务端配置如下:

    <dubbo:application name="xxx" owner="yy"/>
    <dubbo:registry protocol="zookeeper" client="zkclient" address="${dubbo.zk.servers}" group="${dubbo.zk.group}"></dubbo:registry>

    <dubbo:protocol name="dubbo" port="20909"></dubbo:protocol>

    <dubbo:provider retries="0" timeout="6000"></dubbo:provider>

    <dubbo:service interface="xxxx" ref="xxx"></dubbo:service>

dubbo消费端配置:

    <dubbo:application name="${application.name}" owner="${dubbo.application.owner}"/>
    <dubbo:registry protocol="zookeeper" client="zkclient" address="${dubbo.zk.servers}" group="${dubbo.zk.group}"></dubbo:registry>
    <dubbo:protocol name="dubbo" port="${dubbo.protocol.port}"></dubbo:protocol>
    <dubbo:monitor address="${dubbo.monitor.address}"></dubbo:monitor>
    <dubbo:consumer retries="0" timeout="6000" check="false"></dubbo:consumer>

Most helpful comment

@oldratlee,@zouguobing 最终找出原因,是上层客户端异步传染引起的,导致此问题迷惑的原因,是因为上层有多种方式调用,其中一种方式用了异步,导致有时成功,有时失败。开始并没有关注到最上层,也就是C的具体逻辑,D->C->B->A,从D开始异步调用,一路传染,导致B调用A为异步。

All 5 comments

Hi @tangyanbo

可以先再确认一下:



1. 返回的Consumer的请求 是不是 对应你看日志的Provider
。可以通过Consumer调用参数和Provider的收到参数 中特殊值、时间点来确定。

  1. 打印的非NULL值日志输出的地方 , 是不是 对应了Provider接口的返回值(避免日志打印其实是中间的值)。



可能引起这个问题原因:

  • (反)序列化出错。 反序列化Consumer端/序列化在Provider端。

    • 可以先找找,返回值的对象及其包含的对象中 包含没有实现Serializable接口的对象

  • 

返回的数据量太大,Dubbo调用有数据量大小的限制,可以用 payload 属性 来修改 来先规避, 缺省Payload = 8M
    http://dubbo.io/User+Guide-zh.htm#UserGuide-zh-%253Cdubbo%253Aprotocol%252F%253E



PS:
(反)序列化出错、数据量太大,Dubbo本应该是要有出错日志的。

@tangyanbo 我们业务中也出现过,考虑线程上下文异步传染会导致null结果

@zouguobing
和问题相关同学直接交流过,楼上正解。

@oldratlee,@zouguobing 最终找出原因,是上层客户端异步传染引起的,导致此问题迷惑的原因,是因为上层有多种方式调用,其中一种方式用了异步,导致有时成功,有时失败。开始并没有关注到最上层,也就是C的具体逻辑,D->C->B->A,从D开始异步调用,一路传染,导致B调用A为异步。

您好,您说 “是上层客户端异步传染引起的,导致此问题迷惑的原因,是因为上层有多种方式调用” 多种方式 是指什么方式嘛,比如A 发MQ B 消费 B中调了dubbo接口 然后出现了null嘛 。

Was this page helpful?
0 / 5 - 0 ratings