javascript
Spring+Hibernate+Atomikos集成构建JTA的分布式事务--解决多数据源跨库事务
一、概念
分布式事務(wù)
分布式事務(wù)是指事務(wù)的參與者、支持事務(wù)的服務(wù)器、資源服務(wù)器以及事務(wù)管理器分別位于不同的分布式系統(tǒng)的不同節(jié)點之上。簡言之,同時操作多個數(shù)據(jù)庫保持事務(wù)的統(tǒng)一,達(dá)到跨庫事務(wù)的效果。
JTA
JTA,即Java Transaction API,JTA允許應(yīng)用程序執(zhí)行分布式事務(wù)處理———在兩個或多個網(wǎng)絡(luò)計算機(jī)資源上訪問并且更新數(shù)據(jù)。JDBC驅(qū)動程序的JTA支持極大地增強(qiáng)了數(shù)據(jù)訪問能力。
JTA和JTS
Java事務(wù)API(JTA:Java Transaction API)和它的同胞Java事務(wù)服務(wù)(JTS:Java Transaction Service),為J2EE平臺提供了分布式事務(wù)服務(wù)(distributed transaction)。
一個分布式事務(wù)(distributed transaction)包括一個事務(wù)管理器(transaction manager)和一個或多個資源管理器(resource manager)。
一個資源管理器(resource manager)是任意類型的持久化數(shù)據(jù)存儲。
事務(wù)管理器(transaction manager)承擔(dān)著所有事務(wù)參與單元者的相互通訊的責(zé)任。
JTA與JDBC
JTA事務(wù)比JDBC事務(wù)更強(qiáng)大。一個JTA事務(wù)可以有多個參與者,而一個JDBC事務(wù)則被限定在一個單一的數(shù)據(jù)庫連接。下列任一個Java平臺的組件都可以參與到一個JTA事務(wù)中:JDBC連接、JDO PersistenceManager 對象、JMS 隊列、JMS 主題、企業(yè)JavaBeans(EJB)、一個用J2EE Connector Architecture 規(guī)范編譯的資源分配器。
JOTM
JOTM (Java Open Transaction Manager)是一個開源獨立的事務(wù)管理器,支持分布式事務(wù),Spring3.X已經(jīng)不再支持JOTM。
Atomikos
Atomikos TransactionsEssentials是一個為Java平臺提供增值服務(wù)的并且開源類事務(wù)管理器,支持分布式事務(wù),本文所采用的技術(shù)。
Atomikos是目前在分布式事務(wù)管理中做得相當(dāng)不錯的開源軟件。有10年以上的經(jīng)驗,Atomikos保障您的關(guān)鍵事務(wù)和防止昂貴的數(shù)據(jù)丟失在發(fā)生系統(tǒng)故障或事故中.Atomikos支持XA(全局事務(wù))和NON-XA(非全局事務(wù)),NON-XA效率高于XA。本文主要是講XA事件,因為要在不同的數(shù)據(jù)庫中操作多張表。
接下來說一下spring.x+hibernate中集成Atomikos構(gòu)建JTA的分布式事務(wù)
二、Spring.x+Hibernate+Atomikos集成
Spring.x+Hibernate怎么集成此處省略不說,主要講解Spring.x+Atomikos的集成,操作步驟如下:
1、下載Atomikos,需要以下這些包
atomikos-util-1.0.jar cglib-nodep-2.2.2.jar transactions-3.7.0.jar transactions-api-3.7.0.jar transactions-jdbc-3.7.0.jar transactions-jta-3.7.0.jar2、配置
在applicationContext.xml文件當(dāng)中作如下配置
3、在src文件夾下面加入一個transactions.properties文件
# SAMPLE PROPERTIES FILE FOR THE TRANSACTION SERVICE # THIS FILE ILLUSTRATES THE DIFFERENT SETTINGS FOR THE TRANSACTION MANAGER # UNCOMMENT THE ASSIGNMENTS TO OVERRIDE DEFAULT VALUES;# Required: factory implementation class of the transaction core. # NOTE: there is no default for this, so it MUST be specified! # com.atomikos.icatch.service=com.atomikos.icatch.standalone.UserTransactionServiceFactory# Set base name of file where messages are output # (also known as the 'console file'). # # com.atomikos.icatch.console_file_name = tm.out# Size limit (in bytes) for the console file; # negative means unlimited. # # com.atomikos.icatch.console_file_limit=-1# For size-limited console files, this option # specifies a number of rotating files to # maintain. # # com.atomikos.icatch.console_file_count=1# Set the number of log writes between checkpoints # # com.atomikos.icatch.checkpoint_interval=500# Set output directory where console file and other files are to be put # make sure this directory exists! # # com.atomikos.icatch.output_dir = ./# Set directory of log files; make sure this directory exists! # # com.atomikos.icatch.log_base_dir = ./# Set base name of log file # this name will be used as the first part of # the system-generated log file name # # com.atomikos.icatch.log_base_name = tmlog# Set the max number of active local transactions # or -1 for unlimited. # # com.atomikos.icatch.max_actives = 50# Set the default timeout (in milliseconds) for local transactions # # com.atomikos.icatch.default_jta_timeout = 10000# Set the max timeout (in milliseconds) for local transactions # # com.atomikos.icatch.max_timeout = 300000# The globally unique name of this transaction manager process # override this value with a globally unique name # # com.atomikos.icatch.tm_unique_name = tm# Do we want to use parallel subtransactions? JTA's default # is NO for J2EE compatibility # # com.atomikos.icatch.serial_jta_transactions=true# If you want to do explicit resource registration then # you need to set this value to false. # # com.atomikos.icatch.automatic_resource_registration=true # Set this to WARN, INFO or DEBUG to control the granularity # of output to the console file. # # com.atomikos.icatch.console_log_level=WARN# Do you want transaction logging to be enabled or not? # If set to false, then no logging overhead will be done # at the risk of losing data after restart or crash. # # com.atomikos.icatch.enable_logging=true# Should two-phase commit be done in (multi-)threaded mode or not? # Set this to false if you want commits to be ordered according # to the order in which resources are added to the transaction. # # NOTE: threads are reused on JDK 1.5 or higher. # For JDK 1.4, thread reuse is enabled as soon as the # concurrent backport is in the classpath - see # http://mirrors.ibiblio.org/pub/mirrors/maven2/backport-util-concurrent/backport-util-concurrent/ # # com.atomikos.icatch.threaded_2pc=false# Should shutdown of the VM trigger shutdown of the transaction core too? # # com.atomikos.icatch.force_shutdown_on_vm_exit=false4、注入HibernateTemplate模板
a、為bpm庫注入HibernateTemplate模板
b、為center庫注入HibernateTemplate模板
public abstract class CenterDaoSupport<T> extends DaoSupport<T> {protected HibernateTemplate centerHibernateTemplate;/*** HibernateTemplate注入* * @param centerHibernateTemplate*/@Resourcepublic void setCenterHibernateTemplate(HibernateTemplate centerHibernateTemplate) {this.centerHibernateTemplate = centerHibernateTemplate;setHibernateTemplate(centerHibernateTemplate);} }5、編寫業(yè)務(wù)邏輯代碼
@Service(value="userServiceBean") @Transactional public class UserServiceBean implements UserService {@Resource(name="userDaoBean") private UserDao userDao;@Resource(name="userRoleDaoBean") private UserRoleDao userRoleDao;public List<User> queryUser() {return userDao.queryUser();}public void save(User user, UserRole ur) {userDao.save(user); //a處//此處報異常System.out.println(1/0); //b處 ur.setUserId(user.getUid());userRoleDao.save(ur); //c處 } }在執(zhí)行save()方法時會報java.lang.ArithmeticException: / by zero異常,b處的“1/0”有問題,因為除數(shù)不能為0;
如果事務(wù)生效,save()方法會回滾掉,即a處、c處不做save操作,保持事務(wù)的原子性;
如果事務(wù)不起作用,那么a處會執(zhí)行成功,往數(shù)據(jù)庫添加一條記錄;b處拋出異常終止向下執(zhí)行;c處這條代碼不執(zhí)行,導(dǎo)致臟數(shù)據(jù)的出現(xiàn)。
Atomikos的集成到此就結(jié)束了,親!是不是很簡單。
注意
MySQL的驅(qū)動需要5.1.10版本以上,低版本會出現(xiàn)如下錯誤:
java.lang.IllegalArgumentException: null source
總結(jié)
以上是生活随笔為你收集整理的Spring+Hibernate+Atomikos集成构建JTA的分布式事务--解决多数据源跨库事务的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 1. ThreadPoolExecuto
- 下一篇: C++ set的一些用法