《Spring 2.0技术手册》 读书笔记七-Spring的DAO框架(3)-JDBC事务管理

本文内容纲要:《Spring 2.0技术手册》 读书笔记七-Spring的DAO框架(3)-JDBC事务管理

Spring提供了编程式事务管理(programmatic transaction management)与声明式事务管理(declarative transaction management)。由于编程式事务管理会导致Spring框架侵入代码,而且变更复杂,故不赞成使用编程式事务管理。因此该篇笔记以声明式事务管理为主。

事务是一组原子操作的工作单元,在数据库存取中,就是一组SQL指令,它们必须全部执行成功,因为某个原因未全部成功,则先前所有执行过的SQL指令都要被撤销。

1. JDBC的事务管理

try{ connection.setAutoCommit(false); ...//一连串SQL操作 connection.commit(); }catch(SQLException){ //发生错误,撤销所有变更 connection.rollback(); }

2. Spring的事务管理

Spring对JDBC的事务管理加以封装,关键是对org.springframework.transaction.PlatformTransactionManager接口的实现,DataSourceTransactionManager,HibernateTransactionManager等实现了此接口:

public interface PlatformTransactionManager { /** * Return a currently active transaction or create a new one, according to * the specified propagation behavior. * @param definition TransactionDefinition instance (can be null for defaults), * describing propagation behavior, isolation level, timeout etc. * @return transaction status object representing the new or current transaction */ TransactionStatus getTransaction(TransactionDefinition definition) throws TransactionException; /** * Commit the given transaction, with regard to its status. If the transaction * has been marked rollback-only programmatically, perform a rollback. *

If the transaction wasn't a new one, omit the commit for proper * participation in the surrounding transaction. If a previous transaction * has been suspended to be able to create a new one, resume the previous * transaction after committing the new one. *

Note that when the commit call completes, no matter if normally or * throwing an exception, the transaction must be fully completed and * cleaned up. No rollback call should be expected in such a case. *

If this method throws an exception other than a TransactionException, * then some before-commit error caused the commit attempt to fail. For * example, an O/R Mapping tool might have tried to flush changes to the * database right before commit, with the resulting DataAccessException * causing the transaction to fail. The original exception will be * propagated to the caller of this commit method in such a case. * @param status object returned by the getTransaction method */ void commit(TransactionStatus status) throws TransactionException; /** * Perform a rollback of the given transaction. *

If the transaction wasn't a new one, just set it rollback-only for proper * participation in the surrounding transaction. If a previous transaction * has been suspended to be able to create a new one, resume the previous * transaction after rolling back the new one. *

Do not call rollback on a transaction if commit threw an exception. * The transaction will already have been completed and cleaned up when commit * returns, even in case of a commit exception. Consequently, a rollback call * after commit failure will lead to an IllegalTransactionStateException. * @param status object returned by the getTransaction method */ void rollback(TransactionStatus status) throws TransactionException; }

其中,org.springframework.transaction.TransactionDefinition接口的实例定义了事务的隔离程度、传播行为、超时、只读等。

public interface TransactionDefinition { int PROPAGATION_REQUIRED = 0; int PROPAGATION_SUPPORTS = 1; int PROPAGATION_MANDATORY = 2; int PROPAGATION_REQUIRES_NEW = 3; int PROPAGATION_NOT_SUPPORTED = 4; int PROPAGATION_NEVER = 5; int PROPAGATION_NESTED = 6; int ISOLATION_DEFAULT = -1; int ISOLATION_READ_UNCOMMITTED = Connection.TRANSACTION_READ_UNCOMMITTED; int ISOLATION_READ_COMMITTED = Connection.TRANSACTION_READ_COMMITTED; int ISOLATION_REPEATABLE_READ = Connection.TRANSACTION_REPEATABLE_READ; int ISOLATION_SERIALIZABLE = Connection.TRANSACTION_SERIALIZABLE; int TIMEOUT_DEFAULT = -1; /** Return the propagation behavior. */ int getPropagationBehavior(); /** Return the isolation level. */ int getIsolationLevel(); /** Return the transaction timeout. */ int getTimeout(); /*** Return whether to optimize as a read-only transaction. */ boolean isReadOnly(); /** * Return the name of this transaction. Can be null. *

This will be used as the transaction name to be shown in a * transaction monitor, if applicable (for example, WebLogic's). */ String getName(); }

org.springframework.transaction.TransactionStatus代表着一个新的事务发起或已经存在的事务,通过它可以控制事务的执行、设置状态。

public interface TransactionStatus extends SavepointManager { /** * Return whether the present transaction is new (else participating * in an existing transaction, or potentially not running in an * actual transaction in the first place). */ boolean isNewTransaction(); /** * Return whether this transaction internally carries a savepoint, * that is, has been created as nested transaction based on a savepoint. */ boolean hasSavepoint(); /** * Set the transaction rollback-only. This instructs the transaction manager * that the only possible outcome of the transaction may be a rollback, as * alternative to throwing an exception which would in turn trigger a rollback. */ void setRollbackOnly(); /** * Return whether the transaction has been marked as rollback-only * (either by the application or by the transaction infrastructure). */ boolean isRollbackOnly(); /** * Flush the underlying session to the datastore, if applicable: */ void flush(); /** * Return whether this transaction is completed, that is, * whether it has already been committed or rolled back. */ boolean isCompleted(); }

编程事务管理举例:

public class TransactionDAO { private JdbcTemplate jdbcTemplate; private DataSourceTransactionManager transactionManager; private DefaultTransactionDefinition def; public void setDataSource(DataSource dataSource){ jdbcTemplate=new JdbcTemplate(dataSource); transactionManager= new DataSourceTransactionManager(dataSource); def=new DefaultTransactionDefinition(); def.setPropagationBehavior(TransactionDefinition.PROPAGATION_REQUIRED); } public void insert(User user){ TransactionStatus status= transactionManager.getTransaction(def); try{ jdbcTemplate.update("insert into user(name) values('"+user.getName()+"')"); jdbcTemplate.update("insert"); }catch(DataAccessException e){ transactionManager.rollback(status); throw e; } transactionManager.commit(status); } }

声明事务管理:

声明式事务管理依赖它的AOP框架,使用它只需在定义文件中进行配置,事务管理不会侵入所开发的组件,而且便于修改。简单的Bean定义文件配置如下:

org.spring.dao.IUserDAOPROPAGATION_REQUIRED

transactionManager、userDAO使用同一个DataSource,在org.springframework.transaction.interceptor.TransactionProxyFactoryBean代理对象中设置被代理接口、被代理目标实例、事务管理器以及事务属性。这样事务管理会自动介入指定的方法前后。如上,userDAO中以insert开头的方法都会被纳入事务管理,即方法执行过程中发生错误,则方法中所有先前的操作都自动撤回,否则正常提交。

事务属性可以在TransactionDefinition接口中找到。对于目标方法可以加上多个事务属性定义,中间用","隔开。

这样配置后,就可以正常使用UserDAO了,在UserDAO类中不需要增加事务管理代码。即

IUserDAO dao=(IUserDAO)context.getBean("userDAOProxy");dao.insert(user);

也可以设置单独的Interceptor,如下:

org.spring.dao.IUserDAOtransactionInterceptor

**总结:**Spring的学习笔记就到此结束了,基本内容概括的差不多了。随着学习和应用,会对Spring进行深层的补充和理解。

本文内容总结:《Spring 2.0技术手册》 读书笔记七-Spring的DAO框架(3)-JDBC事务管理

原文链接:https://www.cnblogs.com/whuqin/archive/2011/03/13/4982102.html

以上是 《Spring 2.0技术手册》 读书笔记七-Spring的DAO框架(3)-JDBC事务管理 的全部内容, 来源链接: utcz.com/z/362690.html

回到顶部