分布式事务框架Seata的使用

Seata有3个基本组件:
    - Transaction Coordinator(TC):事务协调器,维护全局事务的运行状态,负责协调并驱动全局事务的提交或回滚。
    - Transaction Manager(TM):事务管理器,控制*全局事务*的边界,负责开启一个全局事务,并最终发起全局提交或全局回滚的决议。
    - Resource Manager(RM):资源管理器,控制*分支事务*,负责分支注册、状态汇报,并接收事务协调器的指令,驱动分支(本地)事务的提交和回滚。

全局事务与分支事务:

Seata管理分布式事务的典型生命周期:

    - TM 向 TC 申请开启一个全局事务,全局事务创建成功并生成一个全局唯一的 XID。
    - XID 在微服务调用链路的上下文中传播。
    - RM 向 TC 注册分支事务,将其纳入 XID 对应全局事务的管辖。
    - TM 向 TC 发起针对 XID 的全局提交或回滚决议。
    - TC 调度 XID 下管辖的全部分支事务完成提交或回滚请求。

    至此,seata的协议机制总体上看与 XA 是一致的。但是是有差别的:

    XA 方案的 RM 实际上是在数据库层,RM 本质上就是数据库自身(通过提供支持 XA 的驱动程序来供应用使用)。
    而 Fescar 的 RM 是以二方包的形式作为中间件层部署在应用程序这一侧的,不依赖于数据库本身对协议的支持,当然也不需要数据库支持 XA 协议。这点对于
微服务化的架构来说是非常重要的:应用层不需要为本地事务和分布式事务两类不同场景来适配两套不同的数据库驱动。
    这个设计,剥离了分布式事务方案对数据库在 *协议支持* 上的要求。
    1. 依赖
    <dependency>
        <groupId>com.alibaba.cloud</groupId>
        <artifactId>spring-cloud-alibaba-seata</artifactId>
        <version>2.0.0.RELEASE</version>
    </dependency>
    <dependency>
        <groupId>io.seata</groupId>
        <artifactId>seata-all</artifactId>
        <version>0.8.0</version>
    </dependency>
    2. 配置
    application.properties:就是一些常规配置,可略过
    还剩下3个配置文件:
        1. registry.conf:配置注册中心和配置中心,默认是file。

            该文件包含两部分配置:
            1. 注册中心
            2. 配置中心
                注册中心:
                registry { # 注册中心配置
                      # 可选项:file 、nacos 、eureka、redis、zk
                      type = "nacos" # 指定nacos注册中心,默认是file。由于项目整体使用nacos,所以后续选择nacos

                      nacos {
                        serverAddr = "127.0.0.1:8848"
                        namespace = "public"
                        cluster = "default"
                      }
                      eureka {
                        serviceUrl = "http://localhost:1001/eureka"
                        application = "default"
                        weight = "1"
                      }
                      redis {
                        serverAddr = "localhost:6381"
                        db = "0"
                      }
                      zk {
                        cluster = "default"
                        serverAddr = "127.0.0.1:2181"
                        session.timeout = 6000
                        connect.timeout = 2000
                      }
                      file {
                        name = "file.conf"
                      }
                    }
                配置中心:
                config { # 配置中心
                      # 可选项:file、nacos 、apollo、zk
                      type = "file" # 指向file配置中心,也可以指向nacos等其他注册中心

                      nacos {
                        serverAddr = "localhost"
                        namespace = "public"
                        cluster = "default"
                      }
                      apollo {
                        app.id = "fescar-server"
                        apollo.meta = "http://192.168.1.204:8801"
                      }
                      zk {
                        serverAddr = "127.0.0.1:2181"
                        session.timeout = 6000
                        connect.timeout = 2000
                      }
                      file {
                        name = "file.conf"   # 通过file.conf配置seata参数,指向第二个配置文件
                      }
                    }        
                
        2. file.conf:seata工作规则信息
            该文件的命名取决于registry.conf配置中心的配置
            就是说:file.conf文件名取决于registry的配置中心配置,如果registry配置的配置中心不是file,可以没有改文件。例如:如果配置中心是nacos,这是file.conf文件就不需要了,把file.conf文件内容交给nacos就可

                网络传输配置:
                transport {
                  # tcp udt unix-domain-socket
                  type = "TCP"
                  #NIO NATIVE
                  server = "NIO"
                  #enable heartbeat
                  heartbeat = true
                  #thread factory for netty
                  thread-factory {
                    boss-thread-prefix = "NettyBoss"
                    worker-thread-prefix = "NettyServerNIOWorker"
                    server-executor-thread-prefix = "NettyServerBizHandler"
                    share-boss-worker = false
                    client-selector-thread-prefix = "NettyClientSelector"
                    client-selector-thread-size = 1
                    client-worker-thread-prefix = "NettyClientWorkerThread"
                    # netty boss thread size,will not be used for UDT
                    boss-thread-size = 1
                    #auto default pin or 8
                    worker-thread-size = 8
                  }
                }

                *事务日志存储配置:该部分内容参照account-service中的file.conf配置        
                store {
                  ## store mode: file、db
                  mode = "file"  # 存储方式file、db
                  ## file store
                  file {
                    dir = "sessionStore"
                    # branch session size , if exceeded first try compress lockkey, still exceeded throws exceptions
                    max-branch-session-size = 16384
                    # globe session size , if exceeded throws exceptions
                    max-global-session-size = 512
                    # file buffer size , if exceeded allocate new buffer
                    file-write-buffer-cache-size = 16384
                    # when recover batch read size
                    session.reload.read_size = 100
                    # async, sync
                    flush-disk-mode = async
                  }
                  ## database store
                  db {
                    driver_class = ""
                    url = ""
                    user = ""
                    password = ""
                  }
                }

                *当前微服务在seata服务器中注册的信息配置:
                service {
                  #vgroup->rgroup
                  #必须和服务名一致:${spring.applicaiton.name}
                  vgroup_mapping.${spring.application.name}-fescar-service-group = "default"
                  #only support single node
                  default.grouplist = "127.0.0.1:8091" #seata-server服务器地址,默认是8091
                  #degrade current not support
                  enableDegrade = false
                  #disable
                  disable = false
                }
            
                客户端相关工作的机制
                client {
                  async.commit.buffer.limit = 10000
                  lock {
                    retry.internal = 10
                    retry.times = 30
                  }
                }
            
        3.DataSourceConfig:配置代理数据源实现分支事务,如果没有注入,事务无法成功回滚
                每一个微服务原来自己的数据源都必须使用DataSourceProxy代理,这样seata才能掌控所有事务。
                @Configuration
                public class DataSourceConfig {
                    @Bean
                    @ConfigurationProperties(prefix = "spring.datasource")
                    public DruidDataSource druidDataSource() {
                        return new DruidDataSource();
                    }
                    /**
                     * 需要将 DataSourceProxy 设置为主数据源,否则事务无法回滚
                     *
                     * @param druidDataSource The DruidDataSource
                     * @return The default datasource
                     */
                    @Primary
                    @Bean("dataSource")
                    public DataSource dataSource(DruidDataSource druidDataSource) {
                        return new DataSourceProxy(druidDataSource);
                    }
                }
                
            
    3. 注解
        主业务方法添加全局事务:@GlobalTransactional
        分支业务方法添加本地事务注解:@Transactional

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值