开发过程中,Dubbo常见的问题记录。
1、常见序列化问题
java.io.InvalidClassException: com.danny.commons.pay_real_time.bean.PRTTradeReqTO; local class incompatible: stream classdesc serialVersionUID = 8302474502096138497, local class serialVersionUID = -3714837712158046691
增删改实体(dubbo入参、返回值)字段,dubbo provider和dubbo consumer双方都需要更新jar,保证双方jar版本一直,否则会报序列化问题。
最好保证dubbo provider和dubbo consumer加载的.class相同,否则也可能报错。
2、如果A服务依赖B服务,改完B服务中的model,除了重新部署B服务,也要重新部署A服务,否则调用是会报错:
关键字:Fail to decode request
"exceptionMessage":"com.alibaba.dubbo.rpc.RpcException: Failed to invoke the method getCardTradePackageResult in the service com.danny.service.creditdata. CardTradeDataService. Tried 1 times of the providers [172.30.21.45:4091] (1/1) from the registry zookeeper01. lxfintech.com.config:2181 on the consumer 172.30.21.45 using the dubbo version 2.4.10. Last error is: Failed to invoke remote method: getCardTradePackageResult, provider: dubbo://172.30.21.45:4091/com.danny.service.creditdata.CardTradeDataService? accepts=1000&anyhost=true&application=com.lxjr.bigdata.core-core-app&buffer=8192&charset=UTF-8& check=false&client=netty&default.retries=0&default.timeout=20000&dubbo=2.4.10& interface=com.danny.service.creditdata.CardTradeDataService&iothreads=9& methods=getCardTradePackageResult&payload=88388608&pid=13125&revision=1.0.0-20170712.065521-291& serialization=java&server=netty&side=consumer&timeout=60000×tamp=1499854137330&version=1.0.0-TEST, cause: Fail to decode request due to: RpcInvocation [methodName=getCardTradePackageResult, parameterTypes=[class com.danny.model.parameter.creditdata.cardtrade.CardTradeParameter], arguments=null, attachments={dubbo=2.4.10, input=1698, path=com.danny.service.creditdata.CardTradeDataService, version=1.0.0-TEST}]
总结:只要是decode问题,基本上都是序列化问题,序列化出错
3、dubbo响应超时
关键字:Waiting server-side response timeout
消费者调用异常如下:
cause: Waiting server-side response timeout. start time: 2017-07-28 16:38:36.430, end time: 2017-07-28 16:40:36.457, client elapsed: 16 ms, server elapsed: 120010 ms, timeout: 120000 ms,
在dubbo的provider和consumer的配置文件中,如果都配置了timeout的超时时间,dubbo默认以consumer中配置的时间为准
4、DUBBO Thread pool is EXHAUSTED!
并发测试,500并发下单
表现:消费者调用生产者超时,生产者端根本没接收到请求。查看dubbo admin 发现服务正常。
解决:查看服务器(比如jetty)日志,报错:[DUBBO] Thread pool is EXHAUSTED。
active: 500, core: 500, max: 500可以看出线程不够用了,这是找出正在等待的线程,查看原因……
om.alibaba.dubbo.common.threadpool.support.AbortPolicyWithReport - [DUBBO] Thread pool is EXHAUSTED! Thread Name: DubboServerHandler-10.0.0.77:20703, Pool Size: 500 (active: 500, core: 500, max: 500, largest: 500), Task: 5897697 (completed: 5897197), Executor status:(isShutdown:false, isTerminated:false, isTerminating:false), in dubbo://10.0.0.77:20703!, dubbo version: 2.5.3, current host: 127.0.0.1 16-10-17 00:00:00.033 [New I/O server worker #1-6] WARN org.jboss.netty.channel.DefaultChannelPipeline - [DUBBO] An exception was thrown by a user handler while handling an exception event ([id: 0x3c650867, /10.0.0.83:53184 => /10.0.0.77:20703] EXCEPTION: com.alibaba.dubbo.remoting.ExecutionException: class com.alibaba.dubbo.remoting.transport.dispatcher.all.AllChannelHandler error when process received event .), dubbo version: 2.5.3, current host: 127.0.0.1 com.alibaba.dubbo.remoting.ExecutionException: class com.alibaba.dubbo.remoting.transport.dispatcher.all.AllChannelHandler error when process caught event .
5、com.alibaba.dubbo.remoting.RemotingException: message can not send, because channel is closed
可能是网络原因,consumer与provider网络不通(在consumer telnet 10.5.118.127:20010 不通)
其他原因:provider返回的时候,发现调用provider的线程已经关闭了,可能是consumer 设置timeout时间太短
com.alibaba.dubbo.remoting.RemotingException: message can not send, because channel is closed . url:dubbo://10.5.118.127:20010/com.happycommunity.business.api.user.UserBusinessService?anyhost=true&application=happycommunity-gateway&check=false&codec=dubbo&dubbo=2.6.2&generic=false&heartbeat=60000&interface=com.happycommunity.business.api.user.UserBusinessService&methods=login,register&pid=51701&revision=1.0-SNAPSHOT&side=consumer&timeout=30000×tamp=1544433498918&version=1.0.0
6、Dubbo传输数据过大的问题
当dubbo服务提供层向消费层传输大数据容量的对象时,会受到Dubbo的限制,报类似如下异常
cause: java.io.IOException: Data length too large: 9191772, max payload: 8388608, channel: NettyChannel [channel=[id: 0x2b9e3863, /10.10.16.218:57000 => /10.10.13.37:40784]]\njava.io.IOException: Data length too large: 9191772, max payload: 8388608, channel: NettyChannel [channel=[id: 0x2b9e3863, /10.10.16.218:57000 => /10.10.13.37:40784]]\n\tat com.alibaba.dubbo.remoting.transport.AbstractCodec.checkPayload(AbstractCodec.java:49)\n\tat com.alibaba.dubbo.remoting.exchange.codec.ExchangeCodec.encodeResponse(ExchangeCodec.java:285)\n\tat com.alibaba.dubbo.remoting.exchange.codec.ExchangeCodec.encode(ExchangeCodec.java:77)\n\tat com.alibaba.dubbo.rpc.protocol.dubbo.DubboCountCodec.encode(DubboCountCodec.java:39)\n\tat com.alibaba.dubbo.remoting.transport.netty.NettyCodecAdapter$InternalEncoder.encode(NettyCodecAdapter.java:81)
常见场景:Excel导出、上传文件。
原因:因为dubbo协议采用单一长连接和NIO异步通讯,适合于小数据量大并发的服务调用,以及服务消费者机器数远大于服务提供者机器数的情况。
Hessian协议用于集成Hessian的服务,Hessian底层采用Http通讯,采用Servlet暴露服务。适用场景:传入传出参数数据包较大,提供者比消费者个数多,提供者压力较大,可传文件。
因此比较高效的做法是带上传下载文件的服务使用hessian协议,去普通的服务使用dubbo协议。