dynamic-datasource多数据源事务

news2024/10/7 4:24:59

Spring 事务管理分为编程式和声明式两种 编程式事务指的是通过编码方式实现事务;声明式事务基于 AOP,将具体的逻辑与事务处理解耦(编程式事务在这边不做过多陈述)。

声明式事务有两种方式,一种是在配置文件(XML)中做相关的事务规则声明,另一种是基于 @Transactional 注解的方式。

先看一张思维导图(来自互联网)

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

@Transactional注解

@Transactional实质是使用了JDBC的事务来进行事务控制的
@Transactional基于Spring的动态代理的机制

@Transactional实现原理

1:事务开始时,通过AOP机制,生成一个代理connection对象,并将其放入DataSource实例的某个与DataSourceTransactionManager相关的某处容器中。

在接下来的整个事务中,客户代码都应该使用该connection连接数据库,执行所有数据库命令[不使用该connection连接数据库执行的数据库命令,在本事务回滚的时候得不到回滚](物理连接connection逻辑上新建一个会话session;DataSource与TransactionManager配置相同的数据源)

2:事务结束时,回滚在第1步骤中得到的代理connection对象上执行的数据库命令,然后关闭该代理connection对象(事务结束后,回滚操作不会对已执行完毕的SQL操作命令起作用)

事务失效

通过@Transactional实现原理可以发现;

  1. Spring@Transactional不支持跨数据源事物,Spring 事物控制是基于数据库链接进行的,当数据源切换后,数据库链接切换,事物回滚只能回退,当前持有的链接。
  2. Spring开启事物后,会将当前数据库及数据库链接资源进行线程绑定,导致数据源切换失效(数据源切换执行后,并未获取到新的数据库链接)

怎么解决多数据源问题

新平台目前使用的是@DS注解来切换数据源,通过DynamicDataSourceAnnotationInterceptor我们可以看到,实现的是MethodInterceptor,在通过注解进行数据源切换,由于@Transactional对数据库连接绑定,导致@DS切换不生效;

public Object invoke(MethodInvocation invocation) throws Throwable {
        String dsKey = this.determineDatasourceKey(invocation);
        DynamicDataSourceContextHolder.push(dsKey);

        Object var3;
        try {
            var3 = invocation.proceed();
        } finally {
            DynamicDataSourceContextHolder.poll();
        }

        return var3;
    }

    private String determineDatasourceKey(MethodInvocation invocation) {
        String key = this.dataSourceClassResolver.findKey(invocation.getMethod(), invocation.getThis());
        return key.startsWith("#") ? this.dsProcessor.determineDatasource(invocation, key) : key;
    }

解决方案

由于事务的开启是通过AOP实现的,而service 方法内调用绕过了AOP拦截,为了解决这个问题可以使用

(Tservice)AopContext.currentProxy().test1();

通过@Transactional原理可知@Transactional是单事务,因此在具体的方法上

```java
@Transactional(propagation = Propagation.REQUIRES_NEW)
public void test1(){

但是这样就没法控制多数据源事务;

mybatis-plus解决方案

mybatis-plus官方提供了@DSTransactional注解

@Target({ElementType.TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@Documented
public @interface DSTransactional {
}

在没有seata的情况下,通过DynamicDataSourceAnnotationAdvisor 管理事务,DynamicDataSourceAnnotationAdvisor的拦截器是DynamicLocalTransactionInterceptor

    @Role(2)
    @Bean
    @ConditionalOnProperty(
        prefix = "spring.datasource.dynamic",
        name = {"seata"},
        havingValue = "false",
        matchIfMissing = true
    )
    public Advisor dynamicTransactionAdvisor() {
        DynamicLocalTransactionInterceptor interceptor = new DynamicLocalTransactionInterceptor();
        return new DynamicDataSourceAnnotationAdvisor(interceptor, DSTransactional.class);
    }

具体的大家可以自行了解一下;

应该怎么做

通过上面的说明,想必大家已经知道,我们应该怎样做

    @DSTransactional
    public int addEn(Users users) {

        (Tservice)AopContext.currentProxy().insertUser(users);
        (Tservice)AopContext.currentProxy().insertUser1(users);

        if ("aa".equals(users.getName())) {
            throw new RuntimeException();
        }
        return 1;

    }


    public void insertUser(Users users) {
        usersMapper.insertUser(users);
    }


    public void insertUser1(Users users) {
        usersMapper.insertUser1(users);
    }

usermapper

    @DS("master")
    Long insertUser(Users users);

    @DS("slave")
    Long insertUser1(Users users);

后续改进

Spring Boot整合了Atomikos和Bitronix两个JTA(Java Transaction API)的实现,但在2.3.0的版本中Bitronix不推荐使用Bitronix了。Atomikos提供了两款分布式事务产品级解决方案,分别是ExtremeTransactions和TransactionsEssentials,前者需要商业授权,后者是开源免费使用版本,TransactionsEssentials是免费的,可无缝升级为ExtremeTransactions版本;后续我们可以整合Atomikos,目前若依也给出了整合方案;

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1276684.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Sentinel核心类解读:Node

基本介绍 Sentinel中的簇点链路是由一个个的Node组成的,Node是一个接口。Node中保存了对资源的实时数据的统计,Sentinel中的限流或者降级等功能就是通过Node中的数据进行判断的。 Sentinel中是这样描述Node的: Holds real-time statistics…

异常处理啊

异常处理 异常 程序运行过程中,发生错误导致异常退出(不是程序的语法问题,而是代码的逻辑问题,编译不出错)。 e.g. string 字符串,使用 at 函数访问其中的字符元素时,如果越界,程…

SQL Server数据库部署

数据库简介 使用数据库的必要性 使用数据库可以高效且条理分明地存储数据,使人们能够更加迅速、方便地管理数据。数据库 具有以下特点。 》可以结构化存储大量的数据信息,方便用户进行有效的检索和访问。 》 可以有效地保持数据信息的一致性&#xff0c…

(详细教程)笔记本电脑安装Ubuntu系统

1.前言 老的小米笔记本淘汰了,装一下linux系统玩一下。 使用工具如下:一台小米笔记本pro15.6一个惠普32G U盘一个台式机用于下载镜像等资源 2.下载Ubuntu桌面版 cn.ubuntu.com/download/de… 这里我下载的是 22.04.3 LTS 3.下载烧录工具&#xff0c…

软件设计中如何画各类图之三时序图:理解对象交互顺序的利器

目录 1 前言2 符号及说明2.1 对象(Object)2.2 生命线(Lifeline)2.3 消息(Message)2.4 激活(Activation) 3 画时序图的步骤3.1 确定参与对象3.2 绘制生命线3.3 添加消息3.4 标识激活3…

公共部门生成式人工智能的未来

作者:Dave Erickson 最近,我与 IDC Government Insights 研究副总裁阿德莱德奥布莱恩 (Adelaide O’Brien) 坐下来讨论了全球公共部门生成式人工智能的当前和未来状况。 完整的对话可以按需查看,但我也想强调讨论中的一些要点。 我们的目标是…

【Python表白系列】一起去看流星雨吧!(完整代码)

文章目录 流星雨环境需求完整代码详细分析系列文章流星雨 环境需求 python3.11.4PyCharm Community Edition 2023.2.5pyinstaller6.2.0(可选,这个库用于打包,使程序没有python环境也可以运行,如果想发给好朋友的话需要这个库哦~)【注】 python环境搭建请见:https://want5…

在IDEA中,如何修改Jetty的端口号,操作超简单

在IDEA中的jetty配置中的VM options中填入:-Djetty.portxxxx 如下图:

VSC++: 双进制回文

缘由双进制回文数&#xff0c;一道C程序题&#xff0c;求解&#xff01;&#xff01;&#xff01;&#xff1f;_编程语言-CSDN问答 int 合成100回文(int 数) { int 合 0, 倒 数>10 && 数 < 100 ? 数 / 10 : 数;while (倒)合 * 10, 合 倒 % 10, 倒 / 10, (合…

HT71778 实时音频信号跟踪同步升压转换器的特性

HT71778是一款高功率、全集成升压转换器&#xff0c;集成16mΩ功率开关管和18mΩ同步整流管&#xff0c;为便携式系统提供G效的小尺寸处理方案。 HT71778 实时音频信号跟踪同步升压转换器的特性&#xff1a; ・实时音频信号跟踪的电源供电 SN 短接地, VIN 2.7~4.5V, VOUT 5…

时间复杂度为 O(n^2) 的排序算法 | 京东物流技术团队

对于小规模数据&#xff0c;我们可以选用时间复杂度为 O(n2) 的排序算法。因为时间复杂度并不代表实际代码的执行时间&#xff0c;它省去了低阶、系数和常数&#xff0c;仅代表的增长趋势&#xff0c;所以在小规模数据情况下&#xff0c; O(n2) 的排序算法可能会比 O(nlogn) 的…

数字化智慧工地管理云平台源码(人工智能、物联网)

​智慧工地优势&#xff1a;"智慧工地”将施工企业现场视频管理、建筑起重机械安全监控、现场从业人员管理、物料管理、进度管理、扬尘噪声监测等现场设备有机、高效、科学、规范的结合起来真正实现工程项目业务流与现场各类监控源数据流的有效结合与深度配合&#xff0c;…

【Node.js】笔记梳理 8 - API和JWT

写在最前&#xff1a;跟着视频学习只是为了在新手期快速入门。想要学习全面、进阶的知识&#xff0c;需要格外注重实战和官方技术文档&#xff0c;文档建议作为手册使用 系列文章 【Node.js】笔记整理 1 - 基础知识【Node.js】笔记整理 2 - 常用模块【Node.js】笔记整理 3 - n…

Hdoop学习笔记(HDP)-Part.15 安装HIVE

目录 Part.01 关于HDP Part.02 核心组件原理 Part.03 资源规划 Part.04 基础环境配置 Part.05 Yum源配置 Part.06 安装OracleJDK Part.07 安装MySQL Part.08 部署Ambari集群 Part.09 安装OpenLDAP Part.10 创建集群 Part.11 安装Kerberos Part.12 安装HDFS Part.13 安装Ranger …

Linux 系统是如何收发网络包的?(计算机网络)

一、Linux 网络协议栈 如下是TCP/IP四层网络模型&#xff0c;实际上Linux 网络协议栈与它相似 下图是Linux 网络协议栈 二、Linux 接收网络包的流程 1.网卡是计算机里的一个硬件&#xff0c;专门负责接收和发送网络包&#xff0c;当网卡接收到一个网络包后&#xff0c;会通过…

Leetcode 剑指 Offer II 055. 二叉搜索树迭代器

题目难度: 中等 原题链接 今天继续更新 Leetcode 的剑指 Offer&#xff08;专项突击版&#xff09;系列, 大家在公众号 算法精选 里回复 剑指offer2 就能看到该系列当前连载的所有文章了, 记得关注哦~ 题目描述 实现一个二叉搜索树迭代器类 BSTIterator &#xff0c;表示一个按…

华为云obs在java中的使用

1、申请obs服务。 申请完成后&#xff0c;会获得以下几个配置信息&#xff1a; AK"****************************"; SK"******************************************************"; ENDPOINT"obs.*************************"; BUCKET_NAME&q…

麻吉POS集成:如何无代码开发实现电商平台和CRM系统的高效连接

麻吉POS集成的前沿技术&#xff1a;无代码开发 在竞争激烈的电商市场中&#xff0c;商家们急需一种高效且易于操作的技术手段来实现系统间的快速连接与集成。麻吉POS以其前沿的无代码开发技术&#xff0c;让这一需求成为可能。无代码开发是一种允许用户通过图形用户界面进行编…

STDP突触设计(一)

最近看了很多的STDP的工作原理&#xff0c;比如 SNN系列&#xff5c;学习算法篇(6)脉冲时序依赖可塑性STDP_脉冲时间依赖可塑性-CSDN博客 Spike-Timing Dependent Plasticity - Scholarpedia 这两篇的介绍的代码非常的详细&#xff0c;我就不再赘述了 我设计的STDP的是基于…

了解 ignore_above 参数对 Elasticsearch 中磁盘使用的影响

在 Elasticsearch 中&#xff0c;ignore_above 参数允许你忽略&#xff08;而不是索引&#xff09;长于指定长度的字符串。 这对于限制字段的大小以避免性能问题很有用。 在本文中&#xff0c;我们将探讨 “ignore_above” 参数如何影响 Elasticsearch 中字段的大小&#xff0c…