事务“隔离级别”和“传播行为”

在我们的应用中,有两个很重要的概念:事务的隔离级别和传播方式, 指的是:事务过程中对事务资源的锁定级别和事务过程的行为方式描述

先说事务隔离级别,可以看com.paic.pafa.app.lwc.service.transaction. TransactionDefinition

ISOLATION_READ_UNCOMMITTED

ISOLATION_READ_COMMITTED

ISOLATION_REPEATABLE_READ 

ISOLATION_SERIALIZABLE

这几个级别的含义网上的资料很多,介绍含义的同时又引入一些概念:不可重复读、脏读、幻读等等,一些简单的概念被弄复杂了。我就以数据库资源来简单说一下这几个级别属性。

ISOLATION_READ_UNCOMMITTED:比如A事务新增了一条数据但没有commit,另外B事务能读取到这条数据,这表明事务资源完全没有锁机制,出现脏读;

ISOLATION_READ_COMMITTED:比如A事务做“查询一”得到10条记录,然后做其他事情,这期间另外B事务插入并提交了一条数据,A事务再做了一次同样的查询逻辑“查询二”,这个时候查出11条记录,这表明事务资源提供了类似于单行锁,避免了脏读,但不可重复读(查询一和查询二结果不一样)。

ISOLATION_REPEATABLE_READ:比如A事务做“查询一”得到10条记录,然后做其他事情,这期间另外B事务插入并提交了一条数据,A事务再做了一次同样的查询逻辑“查询二”,这个时候查出还是10条记录。但是如果B事务不是提交,而是删除了10条记录中的一条。A事务是看不到这个变化的,这表明事务资源提供了类似于查询结果集的多行锁,避免了不可重复读,但出现了幻读(一条记录已经不存在了,但在A事务中还继续可见,出现幻觉)

ISOLATION_SERIALIZABLE:最高级别,这表明事务资源提供了类似于表锁,脏度、不可重复读、幻读都不会出现。

 

再说传播方式,可以看com.paic.pafa.app.lwc.service.transaction.support. AbstractPlatformTransactionManager

传播方式实际上来源EJB规范。EJB规范定义了六种:NotSupportedRequiredSupportsRequiresNewMandatoryNever

PAFA相对应的定义了:PROPAGATION_NOT_SUPPORTEDPROPAGATION_REQUIREDPROPAGATION_SUPPORTSPROPAGATION_REQUIRES_NEWPROPAGATION_MANDATORYPROPAGATION_NEVER

这些都代表了什么意思呢?这些都是描述事务过程的行为。

 

1.       PROPAGATION_REQUIRED 如果存在一个事务,则支持当前事务。如果没有事务则开启一个新的事务

methodA(){

dosomethingA();

methodB();

}

# PROPAGATION_REQUIRED   // methodB的事务传播属性为PROPAGATION_REQUIRED

methodB(){

    dosomethingB();

}

如果调用methodA时,如果没有处在事务中,当调用methodB时,事务管理器会打开一个新事务。如果methodA处于一个事务TsA中,在调用methodB时,methodB会自动加入到已有的事务TsA

 

2.       PROPAGATION_SUPPORTS 如果存在一个事务,支持当前事务。如果没有事务,则非事务的执行

methodA(){

dosomethingA();

methodB();

}

# PROPAGATION_SUPPORTS   // methodB的事务传播属性为PROPAGATION_SUPPORTS

methodB(){

    dosomethingB();

}

如果调用methodA时,如果没有处在事务中,当调用methodB时,没有事务保护的运行。如果methodA处于一个事务TsA中,在调用methodB时,methodB会自动加入到已有的事务TsA

 

3.       PROPAGATION_REQUIRES_NEW 总是开启一个新的事务。如果一个事务已经存在,则将这个存在的事务挂起

methodA(){

dosomethingA();

methodB();

}

# PROPAGATION_REQUIRES_NEW   // methodB的事务传播属性为PROPAGATION_REQUIRES_NEW

methodB(){

    dosomethingB();

}

如果调用methodA时,如果没有处在事务中,当调用methodB时,事务管理器会打开一个新事务TsB。如果methodA处于一个事务TsA中,在调用methodB时,事务管理器会将methodA的事务TsA挂起,再打开一个新事务TsB,当methodB运行完成后,再恢复methodA的事务TsA。需要说明的是TsATsB互不影响,也就是说TsB的回滚并不能影响TsA,同样TsA的回滚也不影响TsB

 

4.       PROPAGATION_NOT_SUPPORTED  总是非事务地执行,并挂起任何存在的事务

methodA(){

dosomethingA();

methodB();

}

# PROPAGATION_NOT_SUPPORTED   // methodB的事务传播属性为PROPAGATION_NOT_SUPPORTED

methodB(){

    dosomethingB();

}

如果调用methodA时,如果没有处在事务中,当调用methodB时,没有事务保护的运行。如果methodA处于一个事务TsA中,在调用methodB时,事务管理器会将methodA的事务TsA挂起,没有事务保护的执行methodB,完成后,再恢复methodA的事务TsA

5.       PROPAGATION_NEVER 总是非事务地执行,如果存在一个活动事务,则抛出异常

methodA(){

dosomethingA();

methodB();

}

# PROPAGATION_NEVER   // methodB的事务传播属性为PROPAGATION_NEVER

methodB(){

    dosomethingB();

}

如果调用methodA时,如果没有处在事务中,当调用methodB时,没有事务保护的运行。如果methodA处于一个事务TsA中,在调用methodB时,事务管理器抛出异常

6.       PROPAGATION_MANDATORY 如果已经存在一个事务,支持当前事务。如果没有一个活动的事务,则抛出异常

methodA(){

dosomethingA();

methodB();

}

# PROPAGATION_MANDATORY   // methodB的事务传播属性为PROPAGATION_MANDATORY

methodB(){

    dosomethingB();

}

如果调用methodA时,如果没有处在事务中,当调用methodB时,事务管理器抛出异常。如果methodA处于一个事务TsA中,在调用methodB时,methodB会自动加入到已有的事务TsA

 

你可能感兴趣的:(数据库,活动,ejb)