写在前面
怎么说呢,很多时候,我们只是用别人开源的服务
,一些开源的框架
。
如果我们不能深入到框架底层去分析,理解这些框架的底层的一些实现原理。
那遇到问题的时候,我们只能是阿巴阿巴阿巴!!!这是一种很无奈的现实问题。=_=
所以我们要深入到一些优秀的开源框架去学习,多去理解他们的一些底层,从源码分析处理我们遇到的问题。
今天,我就分享一下,在使用seata
分布式事务,工作中遇到的一些问题,然后是如何去解决的。
问题解决
1.seata异常
异常:
io.seata.core.exception.GlobalTransactionException: Could not found global transaction xid = 192.168.2.121:8091:239779337648214016, may be has finished.
这个问题,seata官方文档有解析:
举例说明:@GlobalTransactional(timeout=60000) public void A(){ call remoting B();//远程调用B服务 local DB operation;}public void B(){}可能原因:1. A 执行的总体时间超过了60000ms,导致全局事务发起了全局回滚,此时A或B方法继续执行DB操作,校验全局事务状态,发现全局事务已经回滚。2. B服务执行超出其设定的readTimeout 返回异常给A并将异常抛出导致全局事务回滚,此时B服务执行DB操作时,校验全局事务状态,发现全局事务已经回滚。3. tc集群节点时间不一致。影响:出现这种情况时,数据会整体回滚至A方法执行前的数据的初态,从数据一致性的视角上看,数据是整体一致的。除了上述情况,如果引用的是`seata-spring-boot-starter`的话,产生这个错误的原因也可能是因为一个bug,目前在1.5版本进行了修复,具体可以参考[issues4020](https://github.com/seata/seata/issues/4020),[PR4039](https://github.com/seata/seata/pull/4039)。
尝试解决:
1.@GlobalTransactional(timeout=60000),timeout*10设置600s,已经很长了。
可最终的效果,也是不能解决问题。
github继续找,有个这样的描述:3438
这位老哥,也遇到了这个问题,官方给出的回答是tc
节点时间要同步。
但是我是单节点,不存在多个tc
节点,还有就是服务器的时间,和数据库的时间,也是同步的。
所以还是没有解决我的问题。
我们出现这个问题,是这样的:多次提交,总会成功那么一两次
。
这就说明了,我们的业务代码,是没啥问题的。
而且出现这个问题,是最近才出现的,之前是不会出现的。
2.尝试从源码方面,去解决,调试seata源码。
这是一个很烦琐的过程,也是一个十分烧脑的,但是呢,我们还是得耐心,一步步调试。
这过程,这里就忽略,因为源码调试,也没找到问题所在。
3.接着从经验和实践分析。
1.为什么之前都好好的? 2.为什么时得时不行?
从这两个问题分析下,可能就是环境的问题导致了,那我们试着还原一下一个干净的seata
服务。
如何进行测试呢?
我们是通过service.vgroupMapping.xxxx_tx_group=default
去找到注册到nacos的seata服务
default表示,找那个集群下的seata服务。
那我们可以改下这个值,改成我们自己新开的一个seata服务,
例如这样
然后,让我们的微服务,连到lls
集群下的seata。然后测试一下。
这测试的效果,也是十分的给力,基本上不会出现这个异常。
那到了,这里,我们就可以得出这样的一个结论:
当seata服务器,注册了过多的服务的时候,seata的负载会增高,导致seata的压力过大。
也就出现了这个异常了。
为什么我们会注册那么多的服务呢?
因为我们使用了多数据源的功能,每个数据源,也会注册到seata去的,这样就导致了seata负载高了。
4.最终的解决办法
增加服务器的资源,seata部署集群,减少单个seata的压力。
好了,今天就先到这里了,溜了溜了溜了!!!^_^
觉得有收获的,帮忙点赞、评论、收藏
一下呗!!!
原文:https://juejin.cn/post/7103901225455714317