一、背景
基于rocketmq官方镜像,启动了dashboard。
官方安装地址:https://rocketmq.apache.org/zh/docs/deploymentOperations/04Dashboard
image.png
二、遇到的问题
如下图,在dashboard的message界面,可以看到具体消息。但是点击RESEND MESSAGE的时候,有时候会报出异常,提示找不到消息。
image.png
三、问题排查
既然消息能在dashboard显示,那么消息肯定是存在的,那么问题就是为什么会查询不到消息。
这里借助了阿里的arthas进行问题排查
3.1 查看日志,定位到问题所在
image.png
3.2 本地调试
下载1.0.0源码,执行程序,发现是可以正常调用的。那么问题就出现在容器上了
3.3 下载arthas
curl -O https://arthas.aliyun.com/arthas-boot.jar
java -jar arthas-boot.jar
3.3 监控方法 MQAdminImpl#queryMessage
[arthas@7]$ watch org.apache.rocketmq.client.impl.MQAdminImpl queryMessage '{params, returnObj, throwExp}' -x 2
image.png
对应的代码片段
image.png
对比本地执行的参数,发现是begin参数不一致。也就是时间的计算有问题
下面是计算时间的方法
image.png
3.4 反编译MessageClientIDSetter#getNearlyTimeFromID
jad org.apache.rocketmq.common.message.MessageClientIDSetter
对比容器里的getNearlyTimeFromID代码,和本地代码进行比较,发现是一样的,所以程序是没问题的
3.5 手动调用getNearlyTimeFromID
#找出类 classLoaderHash 5910e440
sc org.apache.rocketmq.common.message.MessageClientIDSetter -d
#手动调用
ognl '@org.apache.rocketmq.common.message.MessageClientIDSetter@getNearlyTimeFromID("AC11000154873FEBA8610251B99A1858")@getTime()' -X 1 -c 5910e440
如下图,可以看出,执行的结果是1722509310362
image.png
而本地调用,执行的结果是1722480510362
1722509310362-1722480510362=28800000,相差8个小时。可以确定,是容器未设置时区,导致时间错误。
3.6 确认时间
image.png
可以看到,默认容器的时间是少了8个小时的
四、问题处理
可以设置容器的时区,也可以自己打个新的镜像。
我这边由于已经有了基础镜像,所以直接从源码编译,基于基础镜像添加jar的方式,构建了一个新的镜像。问题得到解决