如何使用Entity Framework进行交易?

时间:2009-06-28 14:03:58

标签: entity-framework transactions

如果你有这样的代码:

Something something = new Something();
BlahEntities b = new BlahEntities()    
b.AddToSomethingSet(something);
b.SaveChanges();

如何在事务中运行该添加?

5 个答案:

答案 0 :(得分:55)

ObjectContext有一个可用于管理事务的连接属性。

using (var context = new BlahEntities())
using (var tx = context.BeginTransaction())
{
    // do db stuff here...
    tx.Commit();
}

如果发生异常,事务将被回滚。因为对BeginTransaction()的调用需要并且打开连接,所以可能在扩展方法中包含对BeginTransaction的调用是有意义的。

public static DbTransaction BeginTransaction(this ObjectContext context)
{
    if (context.Connection.State != ConnectionState.Open)
    {
        context.Connection.Open();
    }
    return context.Connection.BeginTransaction();
}

我认为这种方法可能比TransactionScope有用的一种情况是,当您必须访问两个数据源并且只需要对其中一个连接进行事务控制时。我认为在这种情况下,TransactionScope将推广到可能不需要的分布式事务。

答案 1 :(得分:26)

您可以将代码放在交易范围

using(TransactionScope scope = new TransactionScope())
{
    // Your code
    scope.Complete(); //  To commit.
}

TransactionScope位于System.Transactions命名空间中,该命名空间位于同名程序集中(您可能需要手动将其添加到项目中)。

答案 2 :(得分:9)

我知道对于LINQ to SQL,如果没有现有的环境事务(TransactionScope是“环境”事务),数据上下文将为SubmitChanges()创建一个事务。我还没有看到LINQ to Entities的文档记录,但我已经看到行为表明它对于Entity Framework也是如此。

因此,只要您使用一个SubmitChanges()(L2SQL)或SaveChanges()(Linq to Entities)进行所有相关更改,您就可以在不使用TransactionScope的情况下使用。

时需要一个TransactionScope
  1. 使用多个SubmitChanges / SaveChanges为一个事务保存多个更改。
  2. 在一个事务中更新多个数据源(例如,Linq和ASP.NET成员资格SQL提供程序)。
  3. 调用可以自行更新的其他方法。
  4. 我遇到嵌套的TransactionScopes问题。他们应该工作,简单的测试用例可以工作,但是当我进入生产代码时,“内部”事务似乎与外部事务是同一个对象。症状包括“事务已提交,您不能再使用此事务”或“此事务对象已被处置”的错误。内部事务完成后,外部事务中会发生错误。

答案 3 :(得分:1)

using System.Transactions;

using (TransactionScope scope = new TransactionScope())
{
    try
    {
        using(DataContext contextObject = new DataContext(ConnectionString))
        {
            contextObject.Connection.Open();
            // First SaveChange method.
            contextObject.SaveChanges();

            // Second SaveChange method.
            contextObject.SaveChanges();
            //--continue to nth save changes

            // If all execution successful
            scope.Complete();   
       }
    }
    catch(Exception ex)
    {
        // If any exception is caught, roll back the entire transaction and end the scope.
        scope.Dispose();
    }
    finally
    {
        // Close the opened connection
        if (contextObject.Connection.State == ConnectionState.Open)
        {
            contextObject.Connection.Close();
        }
    }
}

查找以下链接,了解详细说明https://msdn.microsoft.com/en-us/data/dn456843.aspx

答案 4 :(得分:0)

在所有版本的Entity Framework中,每当您执行SaveChanges()以在数据库上插入,更新或删除时,框架都会将该操作包装在事务中。此事务仅持续足够长的时间来执行操作然后完成。执行另一个此类操作时,将启动一个新事务。 对于最新实体框架版本:6.0 +

在此处阅读更多内容:EntityFramework and Transaction