无废话8小时学会使用Spring Cloud Alibaba(7)Seata分布式事务

    科技2024-10-17  20

    一 Seata的作用

    开源的分布式事务解决方案,致力于提供高性能和简单易用的分布式事务服务。

    二 下载Seata

    我这里用的是最新版的v1.1.0

    下载seata-server-1.1.0服务端 : 

    下载地址:https://github.com/seata/seata/releases/download/v1.1.0/seata-server-1.1.0.zip 

    1.1.0版本下的conf文件夹:

    三 配置Seata

    1.seata-server-1.1.0seataconf文件夹下修改file.conf

    (1).service模块

    注意: seata1.1.0版本是没有这个模块的(seata0.9.0版本是有的),所以我们需要添加这个模块,我直接下载了个seata0.9.0版本的,把里面的service模块直接拷贝过来,如下:

     

    service {   #vgroup->rgroup   vgroup_mapping.my_test_tx_group = "default"   #only support single node   default.grouplist = "127.0.0.1:8091"   #degrade current not support   enableDegrade = false   #disable   disable = false   #unit ms,s,m,h,d represents milliseconds, seconds, minutes, hours, days, default permanent   max.commit.retry.timeout = "-1"   max.rollback.retry.timeout = "-1" }

     

    这个里面要注意了,seata1.1.0版本修改了名命,需要修改如下:

    将vgroup_mapping 改成驼峰 vgroupMapping,

    另外我自己重新名命,将my_test_tx_group 改成 study_tx_group

    vgroupMapping.study_tx_group = "default"

    (2).store模块

    将mode = "file" 改成 mode = "db"

    将url = "jdbc:mysql://127.0.0.1:3306/seata"

      user = "mysql"

    password = "mysql"

    改成自己的数据库连接(数据库配置后面会讲到)

    url = "jdbc:mysql://192.168.1.12:3306/seata" user = "root" password = "123"

    2.seata-server-1.1.0seataconf文件夹下修改registry.conf

    (1).registry模块

    将type = "file" 改成 type = "nacos"

    将serverAddr = "localhost" 

    改成自己的nacos地址

    serverAddr = "192.168.1.14:8848"

    (2).config模块

    这个模块暂时不需要修改,type = "file" 表示从本地读取file.conf文件(客户端项目里面会把这个文件放进去),

    后期也可以改成从nacos里面读取。

    四 数据库新建库seata

    在192.168.1.12数据库上新建数据库seata,并导入db_store.sql脚本,脚本在seata-server-0.9.0seataconf目录里面,也可以从下面直接拷贝执行

    db_store.sql脚本

     

    -- the table to store GlobalSession data drop table if exists `global_table`; create table `global_table` (   `xid` varchar(128)  not null,   `transaction_id` bigint,   `status` tinyint not null,   `application_id` varchar(32),   `transaction_service_group` varchar(32),   `transaction_name` varchar(128),   `timeout` int,   `begin_time` bigint,   `application_data` varchar(2000),   `gmt_create` datetime,   `gmt_modified` datetime,   primary key (`xid`),   key `idx_gmt_modified_status` (`gmt_modified`, `status`),   key `idx_transaction_id` (`transaction_id`) ); -- the table to store BranchSession data drop table if exists `branch_table`; create table `branch_table` (   `branch_id` bigint not null,   `xid` varchar(128) not null,   `transaction_id` bigint ,   `resource_group_id` varchar(32),   `resource_id` varchar(256) ,   `lock_key` varchar(128) ,   `branch_type` varchar(8) ,   `status` tinyint,   `client_id` varchar(64),   `application_data` varchar(2000),   `gmt_create` datetime,   `gmt_modified` datetime,   primary key (`branch_id`),   key `idx_xid` (`xid`) ); -- the table to store lock data drop table if exists `lock_table`; create table `lock_table` (   `row_key` varchar(128) not null,   `xid` varchar(96),   `transaction_id` long ,   `branch_id` long,   `resource_id` varchar(256) ,   `table_name` varchar(32) ,   `pk` varchar(36) ,   `gmt_create` datetime ,   `gmt_modified` datetime,   primary key(`row_key`) );

    执行后如下:

    五 Seata注册到Nacos

    启动Nacos,再启动Seata,进入Nacos的服务管理-服务列表,会发现有该服务

    六 业务集成分布式事务

    1.在3个业务数据库分别建立对应的回滚日志表

    在用户数据库,商品数据库,订单数据库分别导入db_undo_log.sql脚本,脚本在seata-server-0.9.0seataconf目录下,也可以从下面直接拷贝执行

    db_undo_log.sql脚本

     

    -- the table to store seata xid data -- 0.7.0+ add context -- you must to init this sql for you business databese. the seata server not need it. -- 此脚本必须初始化在你当前的业务数据库中,用于AT 模式XID记录。与server端无关(注:业务数据库) -- 注意此处0.3.0+ 增加唯一索引 ux_undo_log drop table `undo_log`; CREATE TABLE `undo_log` (   `id` bigint(20) NOT NULL AUTO_INCREMENT,   `branch_id` bigint(20) NOT NULL,   `xid` varchar(100) NOT NULL,   `context` varchar(128) NOT NULL,   `rollback_info` longblob NOT NULL,   `log_status` int(11) NOT NULL,   `log_created` datetime NOT NULL,   `log_modified` datetime NOT NULL,   `ext` varchar(100) DEFAULT NULL,   PRIMARY KEY (`id`),   UNIQUE KEY `ux_undo_log` (`xid`,`branch_id`) ) ENGINE=InnoDB AUTO_INCREMENT=1 DEFAULT CHARSET=utf8;

     

    执行后如下

    用户数据库:

    商品数据库:

    订单数据库:

    2 微服务配置

    (1).pom添加seata包

    <!--seata--> <dependency>     <groupId>com.alibaba.cloud</groupId>     <artifactId>spring-cloud-alibaba-seata</artifactId>     <version>2.1.1.RELEASE</version>     <exclusions>         <exclusion>             <artifactId>seata-all</artifactId>             <groupId>io.seata</groupId>         </exclusion>     </exclusions> </dependency> <dependency>     <groupId>io.seata</groupId>     <artifactId>seata-all</artifactId>     <version>1.1.0</version> </dependency>

     

    (2).yml修改

     

    cloud:   alibaba:     seata:       #自定义事务组名称需要与seata-server中的对应       tx-service-group: study_tx_group

    (3).resources目录下添加file.conf文件和registry.conf文件

    其实就是将刚才seata-server-1.1.0seataconf文件夹下的两个文件拷贝过来即可

    3.启动类添加seata自动代理数据源

    添加标签@EnableAutoDataSourceProxy

    @EnableAutoDataSourceProxy @EnableDiscoveryClient @SpringBootApplication @EnableFeignClients public class OrderMain {     public static void main(String[] args) {         SpringApplication.run(OrderMain.class, args);     } }

    4.业务类回滚

    @GlobalTransactional  public void save(Order order){         //这个只是测试,用户买了1件商品,花了10块钱         //添加订单         orderDao.save(order);         //异常测试回滚数据         int i =1/0;         //扣账户余额         userFeignService.decrease(order.getUserId(),10);         //扣库存数量         productFeignService.decrease(order.getProductId(),order.getAmount());     }
    Processed: 0.031, SQL: 8