源码网商城,靠谱的源码在线交易网站 我的订单 购物车 帮助

源码网商城

C#中TransactionScope的使用小结

  • 时间:2021-08-18 02:10 编辑: 来源: 阅读:
  • 扫一扫,手机访问
摘要:C#中TransactionScope的使用小结
TransactionScope是.Net Framework 2.0滞后,新增了一个名称空间。它的用途是为数据库访问提供了一个“轻量级”[区别于:SqlTransaction]的事务。使用之前必须添加对 System.Transactions.dll 的引用。 下列代码就是一个正在创建的事务,这个事务自身还封装了多个数据库查询。只要任意一个 SqlCommand 对象引发异常,程序流控制就会跳出 TransactionScope 的 using 语句块,随后,TransactionScope 将自行释放并回滚该事务。由于这段代码使用了 using 语句,所以 SqlConnection 对象和 TransactionScope 对象都将被自动调用Dispose()释放。由此可见,只需添加很少的几行代码,您就可以构建出一个事务模型,这个模型可以对异常进行处理,执行结束后会 自行清理,此外,它还可以对命令的提交或回滚进行管理。
[u]复制代码[/u] 代码如下:
//创建TransactionScope using (TransactionScope tsCope= new TransactionScope()) {  using (SqlConnection cn2005= new SqlConnection(someSql2005))  {  SqlCommand cmd= new SqlCommand(sqlUpdate, cn2005);  cn2005.Open();  cmd.ExecuteNonQuery();  }  using (SqlConnection cn2005= new SqlConnection(anotherSql2005))  {  SqlCommand cmd= new SqlCommand(sqlDelete, cn2005);  cn2005.Open();  cmd.ExecuteNonQuery();  }  tsCope.Complete(); }
连接字符串关键字(Enlist) SqlConnection.ConnectionString 属性支持关键字 Enlist,该关键字指示 System.Data.SqlClient 是否将检测事务上下文并自动在分布式事务中登记连接。 如果 Enlist=true,连接将自动在打开的线程的当前事务上下文中登记。 如果 Enlist=false,SqlClient 连接不会与分布式事务进行交互。 Enlist 的默认值为 true。 如果连接字符串中未指定 Enlist,若在连接打开时检测到一个,连接将自动在分布式事务中登记。
[u]复制代码[/u] 代码如下:
Server=(local)SQL2005;Database=Northwind;Integrated Security=SSPI;enlist=false
上面所看到的示例中我们使用了TransactionScope的默认设置。TransactionScope有三种模式: [b]TransactionScopeOptions [/b] [b]描述 [/b] [b]Required [/b] 如果已经存在一个事务,那么这个事务范围将加入已有的事务。否则,它将创建自己的事务。 [b]RequiresNew [/b] 这个事务范围将创建自己的事务。 [b]Suppress [/b] 如果处于当前活动事务范围内,那么这个事务范围既不会加入氛围事务 (ambient transaction),也不会创建自己的事务。当部分代码需要留在事务外部时,可以使用该选项。 您可以在代码的任何位置上随是查看是否存在事务范围,具体方法就是查看 System.Transactions.Transaction.Current 属性。如果这个属性为“null”,说明不存在当前事务。 若要更改 TransactionScope 类的默认设置,您可以创建一个 TransactionOptions 对象,然后通过它在 TransactionScope 对象上设置隔离级别和事务的超时时间。TransactionOptions 类有一个 IsolationLevel 属性,通过这个属性可以更改隔离级别,例如从默认的可序列化 (Serializable) 改为ReadCommitted,甚至可以改为 SQL Server 2005 引入的新的快照 (Snapshot) 级别。(请记住,隔离级别仅仅是一个建议。大多数数据库引擎会试着使用建议的隔离级别,但也可能选择其他级别。)此 外,TransactionOptions 类还有一个 TimeOut 属性,这个属性可以用来更改超时时间(默认设置为 1 分钟)。 下列代码中使用了默认的 TransactionScope 对象及其默认构造函数。也就是说,它的隔离级别设置为可序列化 (Serializable),事务的超时时间为 1 分钟,而且 TransactionScopeOptions 的设置为 Required。 TransactionOptions tOpt= new TransactionOptions(); //设置TransactionOptions模式 tOpt.IsolationLevel= IsolationLevel.ReadCommitted; // 设置超时间隔为2分钟,默认为60秒
[u]复制代码[/u] 代码如下:
tOpt.Timeout= new TimeSpan(0,2,0); string cnString= ConfigurationManager.ConnectionStrings["sql2005DBServer"].ConnectionString); using (TransactionScope tsCope= new TransactionScope(TransactionScopeOption.RequiresNew, tOpt)) { using (SqlConnection cn2005= new SqlConnection(cnString) { SqlCommand cmd= new SqlCommand(updateSql1, cn2005); cn2005.Open(); cmd.ExecuteNonQuery(); } tsCope.Complete(); }
嵌套应用 如下列代码,假设 Method1 创建一个 TransactionScope,针对一个数据库执行一条命令,然后调用 Method2。Method2 创建一个自身的 TransactionScope,并针对一个数据库执行另一条命令。   
[u]复制代码[/u] 代码如下:
private void Method1() { using (TransactionScope ts= new TransactionScope(TransactionScopeOption.Required)) { using (SqlConnection cn2005= new SqlConnection()) { SqlCommand cmd= new SqlCommand(updateSql1, cn2005); cn2005.Open(); cmd.ExecuteNonQuery(); } Method2(); ts.Complete(); } } private void Method2() { using (TransactionScope ts= new TransactionScope(TransactionScopeOption.RequiresNew)) { using (SqlConnection cn2005= new SqlConnection()) { SqlCommand cmd= new SqlCommand(updateSql2, cn2005); cn2005.Open(); cmd.ExecuteNonQuery(); } ts.Complete(); } }
[b]总结: [/b]进入和退出事务都要快,这一点非常重要,因为事务会锁定宝贵的资源。最佳实践要求我们在需要使用事务之前再去创建它,在需要对其执行命令前迅速打开连接, 执行动作查询 (Action Query),并尽可能快地完成和释放事务。在事务执行期间,您还应该避免执行任何不必要的、与数据库无关的代码,这能够防止资源被毫无疑义地锁定过长的 时间。 [b]使用注意:[/b]TransactionScope事务需要开启一些服务,(如果数据库不在本地,服务器和客户端都需要开启以下服务和组件服务) [img]http://files.jb51.net/file_images/article/201401/201401170853444.jpg[/img] 以下组件服务需要开启 step1 [img]http://files.jb51.net/file_images/article/201401/201401170853445.png[/img] step2: [img]http://files.jb51.net/file_images/article/201401/201401170853446.jpg[/img]
  • 全部评论(0)
联系客服
客服电话:
400-000-3129
微信版

扫一扫进微信版
返回顶部