程序中事宜控制相关
程序中事务控制相关
程序中事务控制相关
第一次学习数据库访问时,事务的控制基本很简单,大概代码如下:
public class ExampleStep1 { DbConnection GetConnection() { return new OracleConnection(ConfigurationManager.ConnectionStrings["connectionstring"].ConnectionString); } public void Excute() { using (DbConnection con = this.GetConnection()) { con.Open(); DbTransaction transaction = con.BeginTransaction(); try { transaction.Commit(); } catch { transaction.Rollback(); } con.Close(); } } }
但是在业务系统中,我们不可能把所有的业务放在一个数据访问接口里面,实际情况是多个数据访问接口的相互协作,即多个接口同在一个服务接口里面,但是这些接口必须在同一个事务里面,简单的方式就是在业务里面启动事务,因为事务是和数据库连接一起的,所以可以把数据库连接和事务控制放在服务接口里面(当然可以使用委托来实现),
public class ExampleStep2 { DbConnection GetConnection() { return new OracleConnection(ConfigurationManager.ConnectionStrings["connectionstring"].ConnectionString); } public void Excute() { using (DbConnection con = this.GetConnection()) { con.Open(); DbTransaction transaction = con.BeginTransaction(); try { Opt1(con); Opt2(con); transaction.Commit(); } catch { transaction.Rollback(); } con.Close(); } } private void Opt1(DbConnection con) { } private void Opt2(DbConnection con) { } }
但是这种业务逻辑里面参杂事务的做法似乎不合时宜,于是里面会想到TransactionScope,他可以不关联数据库连接,这样可以把事务从数据库的管理剥离出来
public class ExampleStep3 { DbConnection GetConnection() { return new OracleConnection(ConfigurationManager.ConnectionStrings["connectionstring"].ConnectionString); } public void Excute() { using (TransactionScope scope = new TransactionScope()) { Opt1(); Opt2(); scope.Complete(); } } private void Opt1() { using (DbConnection con = this.GetConnection()) { con.Open(); // con.Close(); } } private void Opt2() { using (DbConnection con = this.GetConnection()) { con.Open(); // con.Close(); } } }
尽管现在可以很好的在服务接口控制事务了,但是对于一个纯业务的接口而言,事务似乎也略显多余,如果能够从业务里面剥离事务的控制,但是这种代码基本覆盖所有涉及到数据访问的服务接口,aop是实现这种控制的一个方法之一。spring.net的事务控制也是基于此方式的。
引用:
像TransactionScope一样使用DbTransaction
Java Transaction Design Strategies