spring tx——TransactionManger
TransactionDefinition——事务定义
定义事务属性,包括传播级别、隔离级别、名称、超时、只读等
TransactionStatus——事务状态
事务状态,包含事务对象(jdbc为DataSourceTransactionObject),是否新事务、是否新同步对象、是否只读、是否回滚、是否完成、事务中断对象(SuspendedResourcesHolder实现事务中断,保存中断事务的信息)、保存点对象(jdbc为Savepoint,实现嵌套事务)
DataSourceTransactionObject——事务对象
jdbc中事务对象。
持有一个ConnectionHolder对象,而ConnectionHolder持有Connection对象。
SuspendedResourcesHolder——中断事务对象
用于实现事务挂起,持有一个中断事务suspendedResources(jdbc为ConnectionHolder),中断同步对象集合suspendedSynchronizations。
SavePoint——保存点
保存点用于实现嵌套事务,只有jdbc才有
TransactionManger——事务管理器
AbstractPlatformTransactionManager:实现事务的获取、提交、回滚等主要逻辑
传播级别——Propagation
- PROPAGATION_REQUIRED:支持当前事务,没有事务开启事务
- PROPAGATION_SUPPORTS:支持当前事务,没有事务非事务运行
- PROPAGATION_MANDATORY:支持当前事务,没有事务报错
- PROPAGATION_REQUIRES_NEW:有事务挂起事务,新建事务
- PROPAGATION_NOT_SUPPORTED:有事务挂起事务,非事务执行
- PROPAGATION_NEVER:有事务报错
- PROPAGATION_NESTED:嵌套事务,外层事务回滚,内层也回滚
getTransaction——获取事务
public final TransactionStatus getTransaction(@Nullable TransactionDefinition definition)
throws TransactionException {
TransactionDefinition def = (definition != null ? definition : TransactionDefinition.withDefaults());
//1.封装transaction对象并获取当前事务的ConnectionHolder
Object transaction = doGetTransaction();
//2.当前存在事务,根据事务传播级别处理
if (isExistingTransaction(transaction)) {
return handleExistingTransaction(def, transaction, debugEnabled);
}
if (def.getTimeout() < TransactionDefinition.TIMEOUT_DEFAULT) {
throw new InvalidTimeoutException("Invalid transaction timeout", def.getTimeout());
}
//3.当前不存在事务,根据不同事务传播级别处理
//3.1. 如果传播级别是PROPAGATION_MANDATORY,不存在事务报错
if (def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_MANDATORY) {
throw new IllegalTransactionStateException(
"No existing transaction found for transaction marked with propagation 'mandatory'");
}
//3.2. 如果传播级别是PROPAGATION_REQUIRED、PROPAGATION_REQUIRES_NEW、PROPAGATION_NESTED
else if (def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRED ||
def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRES_NEW ||
def.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NESTED) {
//3.2.1. 中断事务同步管理器中注册的同步对象,封装中断事务对象
SuspendedResourcesHolder suspendedResources = suspend(null);
try {
//3.2.2. 开启新事务
return startTransaction(def, transaction, debugEnabled, suspendedResources);
}
catch (RuntimeException | Error ex) {
//3.2.3. 开启新事务失败,重启中断事务对象中的同步对象
resume(null, suspendedResources);
throw ex;
}
}
//3.3. 其他传播级别,以非事务执行代码,但还是封装TransactionStatus返回
else {
boolean newSynchronization = (getTransactionSynchronization() == SYNCHRONIZATION_ALWAYS);
return prepareTransactionStatus(def, null, true, newSynchronization, debugEnabled, null);
}
}
private TransactionStatus handleExistingTransaction(
TransactionDefinition definition, Object transaction, boolean debugEnabled)
throws TransactionException {
//传播级别为PROPAGATION_NEVER抛错异常
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NEVER) {
throw new IllegalTransactionStateException(
"Existing transaction found for transaction marked with propagation 'never'");
}
//传播级别为PROPAGATION_NOT_SUPPORTED,中断当前事务,以非事务执行
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NOT_SUPPORTED) {
if (debugEnabled) {
logger.debug("Suspending current transaction");
}
Object suspendedResources = suspend(transaction);
boolean newSynchronization = (getTransactionSynchronization() == SYNCHRONIZATION_ALWAYS);
return prepareTransactionStatus(
definition, null, false, newSynchronization, debugEnabled, suspendedResources);
}
//传播级别为PROPAGATION_REQUIRES_NEW,中断当前事务,开启新事务
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_REQUIRES_NEW) {
if (debugEnabled) {
logger.debug("Suspending current transaction, creating new transaction with name [" +
definition.getName() + "]");
}
SuspendedResourcesHolder suspendedResources = suspend(transaction);
try {
return startTransaction(definition, transaction, debugEnabled, suspendedResources);
}
catch (RuntimeException | Error beginEx) {
resumeAfterBeginException(transaction, suspendedResources, beginEx);
throw beginEx;
}
}
//传播级别为PROPAGATION_NESTED,jdbc处理为在当前事务上创建一个保存点
if (definition.getPropagationBehavior() == TransactionDefinition.PROPAGATION_NESTED) {
if (!isNestedTransactionAllowed()) {
throw new NestedTransactionNotSupportedException(
"Transaction manager does not allow nested transactions by default - " +
"specify 'nestedTransactionAllowed' property with value 'true'");
}
if (debugEnabled) {
logger.debug("Creating nested transaction with name [" + definition.getName() + "]");
}
if (useSavepointForNestedTransaction()) {
DefaultTransactionStatus status =
prepareTransactionStatus(definition, transaction, false, false, debugEnabled, null);
status.createAndHoldSavepoint();
return status;
}
else {
// JTA事务的处理
return startTransaction(definition, transaction, debugEnabled, null);
}
}
// 传播级别为PROPAGATION_SUPPORTS、PROPAGATION_REQUIRED以当前事务执行
//省略代码。。。
boolean newSynchronization = (getTransactionSynchronization() != SYNCHRONIZATION_NEVER);
return prepareTransactionStatus(definition, transaction, false, newSynchronization, debugEnabled, null);
}
commit——提交事务
public final void commit(TransactionStatus status) throws TransactionException {
//1.TransactionStatus设置了回滚,执行回滚操作
DefaultTransactionStatus defStatus = (DefaultTransactionStatus) status;
if (defStatus.isLocalRollbackOnly()) {
if (defStatus.isDebug()) {
logger.debug("Transactional code has requested rollback");
}
processRollback(defStatus, false);
return;
}
//2.TransactionStatus的ConnectionHolder设置了回滚,执行回滚操作
if (!shouldCommitOnGlobalRollbackOnly() && defStatus.isGlobalRollbackOnly()) {
if (defStatus.isDebug()) {
logger.debug("Global transaction is marked as rollback-only but transactional code requested commit");
}
processRollback(defStatus, true);
return;
}
//3.执行提交操作
processCommit(defStatus);
}
processCommit方法:
private void processCommit(DefaultTransactionStatus status) throws TransactionException {
try {
boolean beforeCompletionInvoked = false;
try {
boolean unexpectedRollback = false;
prepareForCommit(status);
//触发TransactionSynchronization的beforeCommit和beforeCompletion
triggerBeforeCommit(status);
triggerBeforeCompletion(status);
beforeCompletionInvoked = true;
//有保存点,即嵌套事务,释放保存点
if (status.hasSavepoint()) {
if (status.isDebug()) {
logger.debug("Releasing transaction savepoint");
}
unexpectedRollback = status.isGlobalRollbackOnly();
status.releaseHeldSavepoint();
}
//如果是事务最外层,提交事务
else if (status.isNewTransaction()) {
if (status.isDebug()) {
logger.debug("Initiating transaction commit");
}
unexpectedRollback = status.isGlobalRollbackOnly();
doCommit(status);
}
//默认为false
else if (isFailEarlyOnGlobalRollbackOnly()) {
unexpectedRollback = status.isGlobalRollbackOnly();
}
if (unexpectedRollback) {
throw new UnexpectedRollbackException(
"Transaction silently rolled back because it has been marked as rollback-only");
}
}
catch (UnexpectedRollbackException ex) {
// can only be caused by doCommit
//触发TransactionSynchronization的afterCompletion
triggerAfterCompletion(status, TransactionSynchronization.STATUS_ROLLED_BACK);
throw ex;
}
catch (TransactionException ex) {
// can only be caused by doCommit
//默认为false
if (isRollbackOnCommitFailure()) {
doRollbackOnCommitException(status, ex);
}
else {
//触发TransactionSynchronization的afterCompletion
triggerAfterCompletion(status, TransactionSynchronization.STATUS_UNKNOWN);
}
throw ex;
}
catch (RuntimeException | Error ex) {
//是否触发过TransactionSynchronization的beforeCompletion
if (!beforeCompletionInvoked) {
triggerBeforeCompletion(status);
}
//回滚事务
doRollbackOnCommitException(status, ex);
throw ex;
}
//触发TransactionSynchronization的afterCommit和afterCompletion
try {
triggerAfterCommit(status);
}
finally {
triggerAfterCompletion(status, TransactionSynchronization.STATUS_COMMITTED);
}
}
finally {
//有中断事务恢复中断事务,没有重置TransactionSynchronizationManager
cleanupAfterCompletion(status);
}
}
rollback——回滚事务
public final void rollback(TransactionStatus status) throws TransactionException {
DefaultTransactionStatus defStatus = (DefaultTransactionStatus) status;
processRollback(defStatus, false);
}
processRollback方法:
private void processRollback(DefaultTransactionStatus status, boolean unexpected) {
try {
boolean unexpectedRollback = unexpected;
try {
//触发TransactionSynchronization的beforeCompletion
triggerBeforeCompletion(status);
//有保存点,即嵌套事务,回滚到保存点
if (status.hasSavepoint()) {
if (status.isDebug()) {
logger.debug("Rolling back transaction to savepoint");
}
status.rollbackToHeldSavepoint();
}
//如果是事务最外层,回滚事务
else if (status.isNewTransaction()) {
if (status.isDebug()) {
logger.debug("Initiating transaction rollback");
}
doRollback(status);
}
else {
// 如果事务标记为回滚,将ConnectionHolder标记为回滚
if (status.hasTransaction()) {
if (status.isLocalRollbackOnly() || isGlobalRollbackOnParticipationFailure()) {
doSetRollbackOnly(status);
}
}
// Unexpected rollback only matters here if we're asked to fail early
if (!isFailEarlyOnGlobalRollbackOnly()) {
unexpectedRollback = false;
}
}
}
catch (RuntimeException | Error ex) {
//触发TransactionSynchronization的afterCompletion
triggerAfterCompletion(status, TransactionSynchronization.STATUS_UNKNOWN);
throw ex;
}
//触发TransactionSynchronization的afterCompletion
triggerAfterCompletion(status, TransactionSynchronization.STATUS_ROLLED_BACK);
// Raise UnexpectedRollbackException if we had a global rollback-only marker
if (unexpectedRollback) {
throw new UnexpectedRollbackException(
"Transaction rolled back because it has been marked as rollback-only");
}
}
finally {
//有中断事务恢复中断事务,没有重置TransactionSynchronizationManager
cleanupAfterCompletion(status);
}
}
spring tx——TransactionManger的更多相关文章
- spring tx:advice 和 aop:config 配置事务
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.sp ...
- Spring -- <tx:annotation-driven>注解基于JDK动态代理和CGLIB动态代理的实现Spring注解管理事务(@Trasactional)的区别。
借鉴:http://jinnianshilongnian.iteye.com/blog/1508018 基于JDK动态代理和CGLIB动态代理的实现Spring注解管理事务(@Trasactional ...
- Spring <tx:annotation-driven>注解 JDK动态代理和CGLIB动态代理 区别。
基于JDK动态代理和CGLIB动态代理的实现Spring注解管理事务(@Trasactional)到底有什么区别. 我还是喜欢基于Schema风格的Spring事务管理,但也有很多人在用基于@Tras ...
- [转]spring tx:advice 和 aop:config 配置事务
<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www. ...
- 学习Spring5必知必会(7)~Spring tx
一.spring的事务管理 1.引出事务的经典例子:银行转账发生异常 ✿ 解决:把转出钱和转入钱的业务放到同一个事务空间. ■ 分析转账过程流程: ① 首先,获取 DataSource 对象: ② 其 ...
- spring tx——@EnableTransactionManagement
@EnableTransactionManagement import了TransactionManagementConfigurationSelector,而TransactionManagemen ...
- spring tx:advice事务配置
http://blog.csdn.net/bao19901210/article/details/17226439 http://blog.csdn.net/rong_wz/article/detai ...
- Unable to locate Spring NamespaceHandler for XML schema namespace [http://www.springframework.org/schema/tx]
ERROR - Context initialization failed org.springframework.beans.factory.parsing.BeanDefinitionParsin ...
- Spring 事务管理tx,aop
spring tx:advice事务配置 2016年12月21日 17:27:22 阅读数:7629 http://www.cnblogs.com/rushoooooo/archive/2011/08 ...
随机推荐
- JAVA 字节流 与 字符流 的区别
字节流与和字符流的使用非常相似,两者除了操作代码上的不同之外,是否还有其他的不同呢? 字节流 在操作时本身不会用到缓冲区(内存),是文件本身直接操作的 字符流 在操作时使用了缓冲区,通过缓冲区再操作文 ...
- 新老单点的改造——-理解Cookie、Session、Token
近期参与了新老单点的改造,一直想总结一下,发现这篇文章比较贴切. 整理了如下: 随着交互式Web应用的兴起,像在线购物网站,需要登录的网站等等,马上就面临一个问题,那就是要管理会话,必须记住哪些人登录 ...
- Halcon斑点分析官方示例讲解
官方示例中有许多很好的例子可以帮助大家理解和学习Halcon,下面举几个经典的斑点分析例子讲解一下 Crystals 图中显示了在高层大气中采集到的晶体样本的图像.任务是分析对象以确定特定形状的频率. ...
- activiti学习笔记二
上一篇文章大概讲了下什么是流程引擎,为什么我们要用流程引擎,他的基本原理是啥,以及怎么进行基本的使用,这篇文章我们再讲下其他的一些使用. 删除流程部署 package activiti02; impo ...
- SQL注入之常用工具sqlmap
通常来说,验证一个页面是否存在注入漏洞比较简单,而要获取数据,扩大权限,则要输入很复杂的SQL语句,有时候我们还会对大量的URL进行测试,这时就需要用到工具来帮助我们进行注入了. 目前流行的注入工具有 ...
- 最新的一波Vue实战技巧,不用则已,一用惊人
在Vue中,不同的选项有不同的合并策略,比如 data,props,methods是同名属性覆盖合并,其他直接合并,而生命周期钩子函数则是将同名的函数放到一个数组中,在调用的时候依次调用 在Vue中, ...
- Docker入门——理解Docker的核心概念
1 前言 相信不少人听过这么一句话: 人类的本质是复读机. 在软件开发领域也一样,我们总是想寻找更好地方式复制优秀的逻辑或系统.最核心的方法是抽取通用逻辑和组件,把差异化的东西接口化或配置化,达到复用 ...
- JS动画三剑客——setTimeout、setInterval、requestAnimationFrame
一.前言 前端实现动画效果主要有以下几种方法:CSS3中的transition 和 animation ,Javascript 中可以通过定时器 setTimeout.setinterval,HTML ...
- [Debian]查看进程、终止进程
# jobs -l [1]+ 115 Running nohup /usr/local/bin/dotnet/dotnet/dotnet /usr/share/nginx/asp/publish/Wi ...
- 改变securecrt背景色
下拉菜单中点击 Session Options--->