Spring+JTA+Atomikos+mybatis分布式事务管理
我们平时的工作中用到的Spring事务管理是管理一个数据源的。但是如果对多个数据源进行事务管理该怎么办呢?我们可以用JTA和Atomikos结合Spring来实现一个分布式事务管理的功能。了解JTA可以看一下这篇文章。下面我们看怎么实现分布式事务的。
步骤一:添加pom.xml依赖
步骤二:准备配置文件。jdbc.properties,jta.properties
jdbc.properties
jdbc.driver=com.mysql.jdbc.Driver jdbc.one.url=jdbc:mysql://127.0.0.1:3306/zsyy-pt-ls?useUnicode=true&characterEncoding=UTF-8&zeroDateTimeBehavior=convertToNull
jdbc.one.username=root
jdbc.one.password=esbmysql@ucmed.com jdbc.two.url=jdbc:mysql://127.0.0.1:3306/zsyy-pt-test?useUnicode=true&characterEncoding=UTF-8&zeroDateTimeBehavior=convertToNull
jdbc.two.username=root
jdbc.two.password=esbmysql@ucmed.com
jta.properties
com.atomikos.icatch.registered=true
com.atomikos.icatch.console_file_name=ls2rm.out
com.atomikos.icatch.log_base_name=base_log
com.atomikos.icatch.log_base_dir=lslog
步骤三、配置两个数据源
<bean id="abstractXADataSource" class="com.atomikos.jdbc.AtomikosDataSourceBean" init-method="init" destroy-method="close" abstract="true">
<property name="xaDataSourceClassName" value="com.mysql.jdbc.jdbc2.optional.MysqlXADataSource"/>
<property name="poolSize" value="10"/>
<property name="minPoolSize" value="10"/>
<property name="maxPoolSize" value="30"/>
<property name="borrowConnectionTimeout" value="60"/>
<property name="reapTimeout" value="20"/>
<property name="maxIdleTime" value="60"/>
<property name="maintenanceInterval" value="60"/>
<property name="testQuery">
<value>SELECT 1</value>
</property>
</bean>
<!-- 配置数据源一 -->
<bean id="dataSourceOne" parent="abstractXADataSource">
<property name="uniqueResourceName">
<value>dataSourceOne</value>
</property>
<property name="xaDataSourceClassName" value="com.mysql.jdbc.jdbc2.optional.MysqlXADataSource"/>
<property name="xaProperties">
<props>
<prop key="URL">${jdbc.one.url}</prop>
<prop key="user">${jdbc.one.username}</prop>
<prop key="password">${jdbc.one.password}</prop>
</props>
</property>
</bean>
<!--配置数据源二-->
<bean id="dataSourceTwo" parent="abstractXADataSource">
<property name="uniqueResourceName">
<value>dataSourceTwo</value>
</property>
<property name="xaDataSourceClassName" value="com.mysql.jdbc.jdbc2.optional.MysqlXADataSource" />
<property name="xaProperties">
<props>
<prop key="URL">${jdbc.two.url}</prop>
<prop key="user">${jdbc.two.username}</prop>
<prop key="password">${jdbc.two.password}</prop>
<prop key="pinGlobalTxToPhysicalConnection">true</prop>
</props>
</property>
</bean>
步骤四、配置分布式事务
<!--配置分布式事务-->
<bean id="atomikosTransactionManager" class="com.atomikos.icatch.jta.UserTransactionManager" init-method="init" destroy-method="close">
<property name="forceShutdown" value="false"/>
</bean>
<bean id="atomikosUserTransaction" class="com.atomikos.icatch.jta.UserTransactionImp">
<property name="transactionTimeout" value="300000"/>
</bean>
<!--JTA事务管理器-->
<bean id="springTransactionManager" class="org.springframework.transaction.jta.JtaTransactionManager">
<property name="transactionManager">
<ref bean="atomikosTransactionManager"/>
</property>
<property name="userTransaction">
<ref bean="atomikosUserTransaction"/>
</property>
<property name="allowCustomIsolationLevels" value="true"/>
</bean> <aop:aspectj-autoproxy />
<!--声明式事务-->
<aop:config proxy-target-class="true">
<aop:advisor advice-ref="txAdvice" pointcut="execution(* org.hope.database.one.service.MemberServiceImpl.addMemberAndPoints(..))"/>
</aop:config> <tx:advice id="txAdvice" transaction-manager="springTransactionManager">
<tx:attributes>
<tx:method name="add*" propagation="REQUIRED" read-only="true"/>
<tx:method name="*" propagation="REQUIRED" rollback-for="Exception"/>
</tx:attributes>
</tx:advice>
步骤五、配置mybatis
<!--mybatis的相关配置-->
<bean id="sqlSessionFactoryOne" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSourceOne"/>
<property name="configLocation" value="mybatis-config.xml"/>
<property name="typeAliasesPackage" value="org.hope.database.one.model"/>
<property name="mapperLocations">
<list>
<value>classpath:mapper/one/*.xml</value>
</list>
</property>
</bean> <bean id="sqlSessionFactoryTwo" class="org.mybatis.spring.SqlSessionFactoryBean">
<property name="dataSource" ref="dataSourceTwo"/>
<property name="configLocation" value="mybatis-config.xml"/>
<property name="typeAliasesPackage" value="org.hope.database.two.model"/>
<property name="mapperLocations">
<list>
<value>classpath:mapper/two/*.xml</value>
</list>
</property>
</bean>
<!--配置mybatis映射文件自动扫描-->
<bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="org.hope.database.one"/>
<property name="sqlSessionFactoryBeanName" value="sqlSessionFactoryOne"/>
</bean> <bean class="org.mybatis.spring.mapper.MapperScannerConfigurer">
<property name="basePackage" value="org.hope.database.two"/>
<property name="sqlSessionFactoryBeanName" value="sqlSessionFactoryTwo"/>
</bean>
步骤六、写对应的service
dao和model这个直接看代码吧。
package org.hope.database.one.service; import org.hope.database.one.dao.MemberMapper;
import org.hope.database.two.dao.PointMapper;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service; @Service("memberServiceWa")
public class MemberServiceImpl implements MemberService { @Autowired
private MemberMapper memberMapper; @Autowired
private PointMapper pointMapper; public void addMemberAndPoints(String name, int point) {
memberMapper.addMember(name);
String str = null;
str.equals("wge");//此处会出现异常
pointMapper.addPoint(point);
}
}
步骤七、单元测试
package org.hope.service; import org.hope.database.one.service.MemberService;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner; @RunWith(SpringJUnit4ClassRunner.class)
@ContextConfiguration(locations = {"classpath*:applicationContext.xml"})
public class MemberServiceTest { @Autowired
private MemberService memberServiceWa; @Test
public void addMemberAndPointTest() {
String name = "马化腾";
int points = 50;
memberServiceWa.addMemberAndPoints(name, points);
}
}
https://gitee.com/huayicompany/spring-learn/tree/master/srping-jta-atomikos
参考:
[1] 博客,http://blog.csdn.net/zeroctu/article/details/53116351
[2] 博客,http://blog.csdn.net/sun8288/article/details/8674016,Atomickos中文文档
Spring+JTA+Atomikos+mybatis分布式事务管理的更多相关文章
- 事务隔离级别与传播机制,spring+mybatis+atomikos实现分布式事务管理
1.事务的定义:事务是指多个操作单元组成的合集,多个单元操作是整体不可分割的,要么都操作不成功,要么都成功.其必须遵循四个原则(ACID). 原子性(Atomicity):即事务是不可分割的最小工作单 ...
- Spring事务隔离级别与传播机制详解,spring+mybatis+atomikos实现分布式事务管理
原创说明:本文为本人原创作品,绝非他处转载,转账请注明出处 1.事务的定义:事务是指多个操作单元组成的合集,多个单元操作是整体不可分割的,要么都操作不成功,要么都成功.其必须遵循四个原则(ACID). ...
- spring boot配置mybatis和事务管理
spring boot配置mybatis和事务管理 一.spring boot与mybatis的配置 1.首先,spring boot 配置mybatis需要的全部依赖如下: <!-- Spri ...
- spring整合atomikos实现分布式事务
前言 Atomikos 是一个为Java平台提供增值服务的并且开源类事务管理器,主要用于处理跨数据库事务,比如某个指令在A库和B库都有写操作,业务上要求A库和B库的写操作要具有原子性,这时候就可以用到 ...
- Spring Boot -- Spring Boot之@Async异步调用、Mybatis、事务管理等
这一节将在上一节的基础上,继续深入学习Spring Boot相关知识,其中主要包括@Async异步调用,@Value自定义参数.Mybatis.事务管理等. 本节所使用的代码是在上一节项目代码中,继续 ...
- spring+springMVC+Mybatis架构下采用AbstractRoutingDataSource、atomikos、JTA实现多数据源灵活切换以及分布式事务管理
背景: 1.系统采用SSM架构.需要在10多个MYSQL数据库之间进行切换并对数据进行操作,上篇博文<springMVC+Mybatis(使用AbstractRoutingDataSource实 ...
- spring+springmvc+mybatis+oracle+atomikos+jta实现多数据源事务管理
---恢复内容开始--- 在做项目过程中,遇到了需要一个项目中访问两个数据库的情况,发现使用常规的spring管理事务,导致事务不能正常回滚,因此,采用了jta+atomikos的分布式数据源方式 ...
- spring boot 或 spring 集成 atomikos jta 完成多数据源事务管理
前言:对于事务,spring 不提供自己的实现,只是定义了一个接口来供其他厂商实现,具体些的请看我的这篇文章: https://www.cnblogs.com/qiaoyutao/p/11289996 ...
- 分布式事务、多数据源、分库分表中间件之spring boot基于Atomikos+XADataSource分布式事务配置(100%纯动态)
本文描述spring boot基于Atomikos+DruidXADataSource分布式事务配置(100%纯动态),也就是增加.减少数据源只需要修改application.properties文件 ...
随机推荐
- MicroPython最全资料集锦丨TPYBoard全系列教程之文档+例程源码
MicroPython成功将Python引入到嵌入式领域,近几年MicroPython的发展和普及也证明,Python无疑将在未来几年内快速抢占和蚕食C/C++的份额.包括现在比较火爆的机器人.无人机 ...
- JDBC详解系列(三)之建立连接(DriverManager.getConnection)
在JDBC详解系列(一)之流程中,我将数据库的连接分解成了六个步骤. JDBC流程: 第一步:加载Driver类,注册数据库驱动: 第二步:通过DriverManager,使用url,用户名和密码 ...
- iOS学习——获取iOS设备的各种信息
不管是在Android开发还是iOS开发过程中,有时候我们需要经常根据设备的一些状态或信息进行不同的设置和性能配置,例如横竖屏切换时,电池电量低时,内存不够时,网络切换时等等,我们在这时候需要进行一些 ...
- SGML、HTML、XML、XHTML的关系
我们先看看它们的历史起源: SGML--1986年国际标准化组织出版发布了一个信息管理方面的国际标准(ISO 8879:1986信息处理). HTML 2.0--1995年11月作为RFC 1866发 ...
- jquery/Js属性无效
今天遇到个很奇葩的问题,就是checkbox的onchange时间无效,我一共写了两个checkbox的onchange事件,但就是只有一个能用,本来我以为是jquery的兼容问题,但是换成js还是不 ...
- es7 await/async解决异步问题
最近做项目遇到一个问题,前端调用ie浏览器中的ocx的方法去查询数据,查询完之后ocx给一个返回值,然后js将返回值当参数传入到另外的函数中去做数据处理,但是遇到一个问题是前端需要异步去执行这个过程 ...
- 【有上下界的网络流】ZOJ2341 Reactor Cooling(有上下界可行流)
Description The terrorist group leaded by a well known international terrorist Ben Bladen is bulidi ...
- 入门干货之Electron的.NET实现-Electron.NET
0x01.Electron.NET 1.介绍 Electron是由Github上的一支团队和一群活跃贡献者维护.用HTML,CSS和JavaScript来构建跨平台桌面应用程序的一个开源库. Elec ...
- (3两个例子)从零开始的嵌入式图像图像处理(PI+QT+OpenCV)实战演练
从零开始的嵌入式图像图像处理(PI+QT+OpenCV)实战演练 1综述http://www.cnblogs.com/jsxyhelu/p/7907241.html2环境架设http://www.cn ...
- 异常笔记--java编程思想
开一个新的系列,主要记一些琐碎的重要的知识点,把书读薄才是目的...特点: 代码少,概念多... 1. 基本概念 异常是在当前环境下无法获得必要的信息来解决这个问题,所以就需要从当前环境跳出,就是抛出 ...