Hibernate在应用层对并发事务的控制
Hibernate与事务处理一文中,介绍了事务以及并发事务处理时的问题,和针对于这些问题在数据库层所能做的隔离级别,但是在选择read commit和repeatable read两个隔离级别时,如果考虑到performance和scalability,可以选择一个折衷的方案,也就是在数据库中的隔离级别选择read commit,而通过对应用程序的控制,可以达到repeatable read的效果。Hibernate在程序中控制并发的事务处理上,也有自己的方法,本文在Hibernate与事务处理基础上,对Hibernate的这些并发事务处理方法进行介绍。
数据库隔离级别可以通过设置hibernate的属性文件,来改变数据库默认的隔离级别:
...??
你怎么就不明白呢,如果有a、b两个对象,在第一个事务中先对a进行了读取,存到了它的缓存中。第二个事务对a、b对象都进行了更新,并提交了事务。然后在第一个事务再次对a、b进行读取,它可不会知道a已经被其他事务修改了,读的还是缓存中的a,而b在缓存中没有,所以直接读数据库,因为事务是read commited,所以能读到被第二个事务修改的值,那么a、b两个对象的值一个被修改前的一个是被修改后的,是不一致的,可能会影响业务。
如果事务级别是Repeatable read呢,不管第二个事务怎么修改数据,在第一个事务中后面读到a、b的值始终是第一次读取a当时时刻的值,也就是第二个事务修改前的值,a与b始终是一致的。
所以说hibernate能实现repeatable read的隔离效果这个说法是有问题的。
其实这和hibernate没有关系,即使在开始读取的时候,不可能一下全部把数据读出来,需要一个一个的读,在这期间也有可能后面的数据被其他事务修改了,导致和前面的不一致,所以,要实现Repeatable read的功能,还是要设置Repeatable read的事务隔离级别。 4 楼 Godlikeme 2007-07-14 对于hibernate在应用一层所作的并发处理是持怀疑态度的,
Lock_mode最终还是落在数据库的transaction上,不同数据库的支持不一样。
version这些处理,觉得只是一些小技巧,但在不同的数据库平台,不同的事务隔离级别体现出来的效果不一样。而且要在业务逻辑中写代码去做判断和处理。 5 楼 chillwarmoon 2007-07-14 如果有a、b两个对象,在第一个事务中先对a进行了读取,存到了它的缓存中。第二个事务对a、b对象都进行了更新,并提交了事务。然后在第一个事务再次对 a、b进行读取,它可不会知道a已经被其他事务修改了,读的还是缓存中的a,而b在缓存中没有,所以直接读数据库,因为事务是read commited,所以能读到被第二个事务修改的值,那么a、b两个对象的值一个被修改前的一个是被修改后的,是不一致的,可能会影响业务。<br/>
<br/>
你说的对,但是有没有其他方法用hibernate达到应用一层的repeatable read呢?如果使用数据库的repeatable read,那这样的话应用性能会降低。<br/>
如果没有这样的方法,那hibernate又是怎么样保证既不降低应用性能又能很好的处理并发事务呢? 6 楼 xianyun 2007-07-14 hibernate使用version可以来解决多个操作同时对数据进行更新的问题,它是通过程序的处理来实现的,是脱离事务的,或者事务级别很低,你要把事务设成repeatable read,反而不好用了(是吧)。它只是用来解决并发更新的问题,与事务隔离级别实现的功能是不完全一样的。