1

I have a structure set up with multiple service calls to a WCF service on a server. I have multiple DbContexts instantiated per call. I would like to group some of these calls into a single transaction on the server, while excluding other calls that might occur in the mean time. Is this possible?

My contexts are all managed within a single application on a single server and all contexts use the same connection string.

I am looking for something like

var transKey = transService.BeginTransaction(); // creates a transaction of some kind.
service1.Execute(transKey); // on the server places the execution within the specified transaction.
service2.Execute(transKey); // same here
transService.CommitTransaction(transKey); // Nothing happens until now (allowing other clients to freely utilize service1 without touching the transaction), the transaction occurs, and everything gets cleaned up.

But I may barking up the wrong tree so to speak. Any help in finding a solution to this problem would be useful.

EDIT

What I am wanting to do is have a specified transaction that spans multiple service calls, but not every service call. I am looking for a mechanism to create a transaction, then decide "I want this DbContext action and this other DbConext action, but not this DbContext action part of the transaction". Then have the liberty to hold that transaction until I am ready to execute it. TransactionScope I believe does not give me that kind of control.

I may be wrong but TransactionScope appears to create a single transaction per connection, and any and every DbContext action gets rolled up into the transaction as long as the scope is alive. I need more control over what goes into such and such a transaction.

Price Jones
  • 1,948
  • 1
  • 24
  • 40
  • I think the `TransactionScope` will do the trick https://msdn.microsoft.com/en-us/library/system.transactions.transactionscope(v=vs.110).aspx – Ben Robinson Sep 16 '15 at 12:40
  • If I instantiate a transactionscope will all context calls be part of the transaction? Lets say a second user calls service1.Execute() from a separate client. How can I be sure this second service call and its underlying dbcontext calls are not assumed to be part of the transaction scope? – Price Jones Sep 16 '15 at 12:50
  • I believe it will make the calls across contexts transactional yes, it uses MSDTC under the hood. Multiple service calls, so long as each create their own instances of the context will have their own transactions. – Ben Robinson Sep 16 '15 at 12:54
  • Ah I see. What I am wanting to do is have a specified transaction that spans multiple service calls, but not every service call. I am looking for a mechanism to create a transaction, then decide "I want this DbContext action and this other DbConext action, but not this DbContext action part of the transaction". Then have the liberty to hold that transaction until I am ready to execute it. TransactionScope I believe does not give me that kind of control. – Price Jones Sep 16 '15 at 13:00
  • I could be wrong but I don't think you could make multiple service calls transactional, they run on separate threads. No you can't pick and chose which contexts take part in the transaction. – Ben Robinson Sep 16 '15 at 13:24

1 Answers1

0

I would use distributed transactions but use the TransactionInterop.GetTransmitterPropagationToken method to pass the transaction token to the service calls that you want to participate in the transaction. This also means that you'll need to modify the services to take in the transaction id. Also, be careful with using distributed transactions across multiple appdomains, the appdomain must be kept alive until the transaction is either committed or rolled back, otherwise the transaction will not be commitable.

http://blogs.microsoft.co.il/sasha/2010/04/30/propagating-a-transaction-across-appdomains/

TransactionScope throws TransactionAbortedException when Disposed

http://blogs.msdn.com/b/florinlazar/archive/2008/02/20/flowing-or-propagating-transactions-in-net-blog-entry-under-construction.aspx

Community
  • 1
  • 1
Hasani Blackwell
  • 2,026
  • 1
  • 13
  • 10