Transactions in the Entity Framework

October 2, 2010, (updated on September 8, 2014), 2 comments, Software Development

First, I’ll show an example of the correct usage of an Entity Framework’s ObjectContext. At the beginning of the usage block, the ObjectContext is created; at the end it will be disposed (see using-Keyword).

using (var ctx = new MyObjectContext()) {
    // do your stuff
    ctx.SaveChanges();
}

Usually the code in the using block is not a whole transaction. The call of the method SaveChanges opens a new database connection, starts a new transaction, writes all changes and commits the transaction if no problems occurred. Every call of SaveChanges has its own transaction. If you want to call the SaveChanges method multiple times but in only one transaction, you have to manage the transaction manually.

The following extension method helps opening a connection and handling a transaction:

public static class ObjectContextExtensions
{
    public static void DoTransaction(this ObjectContext context, Action<DbTransaction> action)
    {
        DoTransaction(context, false, action);
    }

    public static void DoTransaction(this ObjectContext context, bool manualCommit, Action<DbTransaction> action)
    {
        context.Connection.Open();
        try
        {
            using (var tx = context.Connection.BeginTransaction())
            {
                try
                {
                    action(tx);
                    if (!manualCommit)
                        tx.Commit();
                }
                catch
                {
                    tx.Rollback();
                    throw; 
                }
            }
        }
        finally
        {
            context.Connection.Close();
        }
    }
}

This extension method can be used as follows:

using (var ctx = new MyObjectContext() 
{
    ctx.DoTransaction(tx => 
    {
        // do your stuff
        ctx.SaveChanges();
    }); 
}

There is an other approach to manage transactions. With the TransactionScope class it is easier to create a transaction. This way the application doesn’t create a SqlTransaction but a DistributedTransaction which can work over multiple ObjectContexts. In most usages such a transaction isn’t needed. Another point with distributed transactions is, that the “Distributed Transaction Service” must be running.

using (var tx = new TransactionScope() 
{
    using (var ctx = new MyObjectContext()) 
    {
        // do your stuff
        ctx.SaveChanges();
    }
    tx.Complete();
}
Tweet about this on TwitterShare on FacebookEmail this to someoneShare on TumblrShare on LinkedIn

Tags: , , ,

2 responses to “Transactions in the Entity Framework”

  1. Kris says:

    Hi,

    I liked the article, can you please post working sample of using transaction extension. I hope it will solve my nested transactions should commit individually despite of other transaction being failed.

    Thanks,
    Kris

Leave a Reply

Your email address will not be published. Required fields are marked *

To create code blocks or other preformatted text, indent by four spaces:

    This will be displayed in a monospaced font. The first four 
    spaces will be stripped off, but all other whitespace
    will be preserved.
    
    Markdown is turned off in code blocks:
     [This is not a link](http://example.com)

To create not a block, but an inline code span, use backticks:

Here is some inline `code`.

For more help see http://daringfireball.net/projects/markdown/syntax