FlushMode属性与transaction(spring注入的事务)
一、参见hibernate的api
http://tool.oschina.net/apidocs/apidoc?api=hibernate-3.6.10
http://tool.oschina.net/apidocs/apidoc?api=hibernate-4.1.4
说明:贴出两个版本的原因在于FlushMode属性在3.6与4.1版本的设置有所不同,3.6的FlushMode属性是一个Class类,而4.1已更换了Enum。
二、 FlushMode属性(策略)
在org.hibernate Class FlushMode中这样解释它的作用:Represents a flushing strategy. The flush process synchronizes database state with session state by detecting state changes and executing SQL statements.
代表一个flushing(刷新)的策略,它将通过改变session的状态和执行SQL的状态来处理线程中的数据。
AUTO:
在确保查询从不会返回脏数据的情况下,在查询前刷新Session。
MANUAL:
Session永远只会在应用程序调用
Session.flush()方法时才会刷新。
说明:
1. Session:Session接口是Hibernate向程序提供操纵数据库的最主要接口,是单线程对象,它提供了基本的保存、更新、删除和查询方法。它有一个缓存,保存了持久化对象,当清理缓存时,按照这些持久化对象同步更新数据库。根据Session的定义,可以知道刷新Session也就刷新了数据库。
2.调用Session.flush()方法,不管FlushMode被设置成任何策略,均会将刷新Session,使其中的缓存数据同步至数据库。
3.ALWAYS与AUTO的区别:从API看出,AUTO的解释Session刷新较ALWAYS多了一个“sometimes ”,说明AUTO并不会像ALWAYS那样总是刷新Session,那它在何时才会刷新呢?当hibernate缓存中的对象被改动之后,会被标记为脏数据(即与数据库不同步了)。当 session设置为FlushMode.AUTO时,hibernate在进行查询的时候会判断缓存中的数据是否为脏数据,是则刷数据库,不是则不刷,而always是直接刷新,不进行任何判断。很显然auto比always要高效得多。
4.设置FlushMode.MANUAL,在操作过程中hibernate会将事务设置为readonly,所以在增加、删除或修改操作过程中会出现如下错误:
org.springframework.web.util.NestedServletException: Request processing failed; nested exception is org.springframework.dao.InvalidDataAccessApiUsageException: Write operations are not allowed in read-only mode (FlushMode.MANUAL): Turn your Session into FlushMode.COMMIT/AUTO or remove 'readOnly' marker from transaction definition. |