SpringCloud系列之Nacos+Dubbo+Seata应⽤篇
⽬录
前⾔
本⽂接上篇⽂章继续展开,本次在原先集成Nacos和Dubbo基础上增加分布式事务Seata组件,之前在中也提及到Seata的集成,只不过原先Seata使⽤都是基于“file”展开,在本篇中将介绍如何基于nacos进⾏配置以及Dubbo和Seata的集成验证。
项⽬版本
spring-boot.version:2.2.5.RELEASE
spring-cloud.version:Hoxton.SR3
nacos.version:1.3.2
dubbo.version:2.6.9/2.7.6
seata.version:1.3.0
关注本⽂末尾,回复“666”获取常⽤开发⼯具包,内含常⽤开发组件(Nacos,Seata等),节省FQ下载时间。
项⽬说明
项⽬模块说明如下:
前端请求接⼝请求cloud-web模块保留接⼝,从⽽调⽤相应业务微服务模块,执⾏业务逻辑后响应前端请求。
⽀付模块对外提供Dubbo服务,其余服务采⽤Feign进⾏通讯,⽤户模块⽰例中未涉及相关业务调⽤。
Dubbo 2.6.x 和 Dubbo 2.7.x 除了依赖不⼀样,其余配置项基本⼀样,这边就不再单独进⾏区分说明,详情请查阅本⽂⽂末项⽬源码,有进⾏区分说明。
Nacos服务
Nacos服务端部署请查阅
Seata服务
进⼊Seata配置⽬录下,编辑f配置⽂件,将registry配置项中type配置项配置成"nacos",并配置nacos相关配置,具体如下
registry {
# file 、nacos 、eureka、redis、zk、consul、etcd3、sofa
type = "nacos"
nacos {
application = "seata-server"
serverAddr = "127.0.0.1:8848"
group = "SEATA_GROUP"
namespace = "public"
cluster = "default"
username = ""
password = ""
}
}
配置完registry配置项后将config配置项也配置成“nacos”,具体如下config {
# file、nacos 、apollo、zk、consul、etcd3
type = "nacos"
nacos {
serverAddr = "127.0.0.1:8848"
namespace = "public"
group = "SEATA_GROUP"
username = ""
password = ""
}
}
调整完后启动Seata服务即可在Nacos后台看到已注册的服务,如下图
订单模块
其余模块本次未进⾏任何调整,只在订单模块中增加Dubbo相关配置部分l如下,完整信息请查阅本⽂⽂末项⽬源码
<!--nacos discovery-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-discovery</artifactId>
<exclusions>
<exclusion>
<groupId>com.alibaba.nacos</groupId>
<artifactId>nacos-client</artifactId>
</exclusion>
</exclusions>
</dependency>
<!--nacos config-->
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-starter-alibaba-nacos-config</artifactId>
<exclusions>
<exclusion>
<groupId>com.alibaba.nacos</groupId>
<artifactId>nacos-client</artifactId>
</exclusion>
</exclusions>
</dependency>
<!--dubbo-->
<dependency>
<groupId>com.alibaba.boot</groupId>
<artifactId>dubbo-spring-boot-starter</artifactId>
<version>0.2.1.RELEASE</version>
</dependency>
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo</artifactId>
<version>2.6.9</version>
</dependency>
<!--dubbo nacos-->
<dependency>
<groupId>com.alibaba</groupId>
<artifactId>dubbo-registry-nacos</artifactId>
<version>2.6.7</version>
<exclusions>
<exclusion>
<groupId>com.alibaba.nacos</groupId>
<artifactId>nacos-client</artifactId>
</exclusion>
</exclusions>
</dependency>
<!--nacos-->
<dependency>
<groupId>com.alibaba.nacos</groupId>
<artifactId>nacos-client</artifactId>
<version>1.3.2</version>
</dependency>
<dependency>
<groupId>ioty</groupId>
<artifactId>netty-all</artifactId>
<version>4.1.31.Final</version>
</dependency>
<!-- seata-->
<dependency>
springcloud和springboot<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-seata</artifactId>
<version>2.2.0.RELEASE</version>
<exclusions>
<exclusion>
<groupId>io.seata</groupId>
<artifactId>seata-spring-boot-starter</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>io.seata</groupId>
<artifactId>seata-spring-boot-starter</artifactId>
<version>1.3.0</version>
</dependency>
application.properties
dubbo.application.name=order-service
# dubbo扫描包路径
dubbo.scan.base-packages=com.der.service
# dubbo协议
dubbo.protocol.name=dubbo
# 随机端⼝
dubbo.protocol.port=-1
# zookeeper地址
spring.main.allow-bean-definition-overriding=true
OrderService.java
@RestController
public class OrderService implements OrderFacade {
@Autowired
private TbOrderMapper tbOrderMapper;
@Autowired
private CartFacade cartFacade;
@Autowired
private GoodsFacade goodsFacade;
@Autowired
private WalletFacade walletFacade;
// Dubbo服务消费
@Reference(check = false)
DPayFacade dPayFacade;
/**
* <p >
* 功能:新增订单
* </p>
* @param cartId 购物车ID
* @author wuyubin
* @date 2020年05⽉22⽇
* @return
*/
@Override
public void addOrder(Long cartId) {
CartDTO cart = CartById(cartId);
TbOrder order = new TbOrder();
order.UserId());
order.GoodsId());
order.setOrderNo(String.valueOf(System.currentTimeMillis()));
order.setCreateTime(System.currentTimeMillis());
order.CreateTime());
order.setIsDeleted(Byte.valueOf("0"));
// 新增订单
tbOrderMapper.insert(order);
// 删除购物车(Feign)
cartFacade.deleteCartById(cartId);
GoodsDTO goods = GoodsId());
// 扣减库存(Feign)
goodsFacade.Id());
/
/ 扣减⾦额(Feign)
walletFacade.UserId(),Money());
// 记录⽀付消息(Dubbo调⽤)
throw new RuntimeException();
}
}
新增引⽤⽀付模块Dubbo服务,ToPay("wuyubin");
⽀付模块
⽀付模块在原先基础上增加Seata依赖,部分pom信息如下
<dependency>
<groupId>com.alibaba.cloud</groupId>
<artifactId>spring-cloud-alibaba-seata</artifactId>
<version>2.2.0.RELEASE</version>
<exclusions>
<exclusion>
<groupId>io.seata</groupId>
<artifactId>seata-spring-boot-starter</artifactId>
</exclusion>
</exclusions>
</dependency>
<dependency>
<groupId>io.seata</groupId>
<artifactId>seata-spring-boot-starter</artifactId>
<version>1.3.0</version>
</dependency>
application.properties
# seata配置
#ludes-for-auto-proxying=firstClassNameForExclude,secondClassNameForExclude
seata.application-id=pay-service
# 事务分组名
<-service-group=pay-service_tx_group
# 默认开启数据源⾃动代理
seata.use-jdk-proxy=false
DPayService.java
@Service
public class DPayService implements DPayFacade {
@Autowired
TbPayMapper tbPayMapper;
@Override
public String goToPay(String userName) {
String xid = XID();
System.out.println("pay.seata.xid:"+xid);
System.out.println("hod:goToPay request "+userName);
TbPay pay = new TbPay();
pay.setMoney(new BigDecimal("5"));
pay.setStatus(Byte.valueOf("1"));
tbPayMapper.insert(pay);
return "hod:goToPay result:" + userName + " pay success";
}
}
调整完启动⽀付模块后,启动过程中发现⼀⾏报错⽇志,信息如下
no available service 'null' found, please make sure registry config correct
请求后果然在⽀付模块报如下错误
Caused by: xception.RmTransactionException: Runtime
Caused by: ption.FrameworkException: No available service
看信息应该是缺少服务,后来经过⼀点点排查后,最终确认是这⼀⾏配置项导致,将
seata.service.vgroup-mapping.pay-service_tx_group=default
先了解下该⾏配置项主要作⽤,原来是靠此配置项⽤于查询TC服务的。
那是不是只要添加这⾏配置就可以了呢,重新将seata配置信息调整⾄“nacos”,根据命名规则尝试创建以下配置项
配置创建成功后,在⽀付模块后台⽴马看到有⽇志输出
2020-09-14 15:58:43.284 ERROR 28292 --- [eoutChecker_2_1] NettyClientChannelManager : no available service 'null' found, please make sure registry config correct
2020-09-14 15:58:53.252 ERROR 28292 --- [eoutChecker_1_1] NettyClientChannelManager : no available service 'null' found, please make sure registry config correct
2020-09-14 15:58:53.285 ERROR 28292 --- [eoutChecker_2_1] NettyClientChannelManager : no available service 'null' found, please make sure registry config correct
2020-09-14 15:59:02.853 INFO 28292 --- [-localhost_8848] fig.impl.ClientWorker : [fixed-localhost_8848] [polling-resp] config changed. dataId=service.vgroupMapping.pay-service_tx_group, group=SEATA_GROUP
2020-09-14 15:59:02.853 INFO 28292 --- [-localhost_8848] fig.impl.ClientWorker : get changedGroupKeys:[service.vgroupMapping.pay-service_tx_group+SEATA_GROUP]
2020-09-14 15:59:02.857 INFO 28292 --- [-localhost_8848] fig.impl.ClientWorker : [fixed-localhost_8848] [data-received] dataId=service.vgroupMapping.pay-service_tx_group, group=SEATA_GROUP, tenant=null, md5=c21f969b 2020-09-14 15:59:02.857 INFO 28292 --- [-localhost_8848] c.a.fig.impl.CacheData : [fixed-localhost_8848] [notify-context] dataId=service.vgroupMapping.pay-service_tx_group, group=SEATA_GROUP, md5=c21f969b5f03d33d4 2020-09-14 15:59:02.858 INFO 28292 --- [-localhost_8848] c.a.fig.impl.CacheData : [fixed-localhost_8848] [notify-ok] dataId=service.vgroupMapping.pay-service_tx_group, group=SEATA_GROUP, md5=c21f969b5f03d33d43e04 2020-09-14 15:59:02.858 INFO 28292 --- [-localhost_8848] c.a.fig.impl.CacheData : [fixed-localhost_8848] [notify-listener] time cost=1ms in ClientWorker, dataId=service.vgroupMapping.pay-service_tx_group, group=SEATA_G 2020-09-14 15:59:03.253 INFO 28292 --- [eoutChecker_1_1] com.alibaba.nacos.client.naming : new ips(1) service: SEATA_GROUP@@seata-server@@default -> [{"instanceId":"192.168.2.241#8091#default#SEATA_GROUP@@seata-se 2020-09-14 15:59:03.254 INFO 28292 --- [eoutChecker_1_1] com.alibaba.nacos.client.naming : current ips:(1) service: SEATA_GROUP@@seata-server@@default -> [{"instanceId":"192.168.2.241#8091#default#SEATA_GROUP@@seata 2020-09-14 15:59:03.254 INF
O 28292 --- [eoutChecker_1_1] com.alibaba.nacos.client.naming : [LISTENER] adding SEATA_GROUP@@seata-server with default to listener map
2020-09-14 15:59:03.256 INFO 28292 --- [eoutChecker_1_1] NettyClientChannelManager : will connect to 192.168.2.241:8091
2020-09-14 15:59:03.258 INFO 28292 --- [eoutChecker_1_1] pcty.NettyPoolableFactory : NettyPool create channel to transactionRole:TMROLE,address:192.168.2.241:8091,msg:< RegisterTMRequest{applicationId='pay-service', tra
2020-09-14 15:59:03.281 INFO 28292 --- [eoutChecker_2_1] NettyClientChannelManager : will connect to 192.168.2.241:8091
2020-09-14 15:59:03.281 INFO 28292 --- [eoutChecker_2_1] pcty.RmNettyRemotingClient : RM will register :jdbc:mysql://127.0.0.1:3306/spring-cloud
2020-09-14 15:59:03.283 INFO 28292 --- [eoutChecker_2_1] pcty.NettyPoolableFactory : NettyPool create channel to transactionRole:RMROLE,address:192.168.2.241:8091,msg:< RegisterRMRequest{resourceIds='jdbc:mysql://127 2020-09-14 15:59:03.305 INFO 28292 --- [eoutCh
ecker_2_1] pcty.RmNettyRemotingClient : register RM success. client version:1.3.0, server version:1.3.0,channel:[id: 0x15ef339d, L:/192.168.2.241:64550 - R:/192.168.2.241:8091] 2020-09-14 15:59:03.305 INFO 28292 --- [eoutChecker_1_1] pcty.TmNettyRemotingClient : register TM success. client version:1.3.0, server version:1.3.0,channel:[id: 0xd4e407be, L:/192.168.2.241:64548 - R:/192.168.2.241:8091] 2020-09-14 15:59:03.313 INFO 28292 --- [eoutChecker_1_1] pcty.NettyPoolableFactory : register success, cost 39 ms, version:1.3.0,role:TMROLE,channel:[id: 0xd4e407be, L:/192.168.2.241:64548 - R:/192.168.2.241:8091]
2020-09-14 15:59:03.313 INFO 28292 --- [eoutChecker_2_1] pcty.NettyPoolableFactory : register success, cost 26 ms, version:1.3.0,role:RMROLE,channel:[id: 0x15ef339d, L:/192.168.2.241:64550 - R:/192.168.2.241:8091]
感觉有戏,再次请求接⼝,果然不再报错,提⽰事务回滚成功,其余模块也提⽰回滚成功,另外数据也正常,⾄此就可以使⽤啦。
pay.seata.xid:192.168.2.241:8091:48803259719028736
2020-09-14 16:06:44.006 INFO 28292 --- [ch_RMROLE_1_1_8] p.c.RmBranchRollbackProcessor : rm handle branch rollback process:xid=192.168.2.241:8091:48803259719028736,branchId=48803260146847744,branchType=AT,resourc 2020-09-14 16:06:44.010 INFO 28292 --- [ch_RMROLE_1_1_8] AbstractRMHandler : Branch Rollbacking: 192.168.2.241:8091:48803259719028736 48803260146847744 jdbc:mysql://127.0.0.1:3306/spring-cloud
2020-09-14 16:06:44.061 INFO 28292 --- [ch_RMROLE_1_1_8] d.undo.AbstractUndoLogManager : xid 192.168.2.241:8091:48803259719028736 branch 48803260146847744, undo_log deleted with GlobalFinished
2020-09-14 16:06:44.063 INFO 28292 --- [ch_RMROLE_1_1_8] AbstractRMHandler : Branch Rollbacked result: PhaseTwo_Rollbacked
参考资料
系列⽂章
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论