2014-01-13 70 views
4

所以,我有兩個數據庫...用戶數據庫和另一個數據庫,還包含一個用戶表。兩者都有電子郵件字段。我想同時更新兩個電子郵件字段。確保完整性超過2個數據庫

(簡化)的代碼看起來是這樣的:

using(var db1 = new Db1Context()) 
using(var db2 = new Db2Context()) 
{ 
    db1.Users.Single(u => u.Email == oldEmail).Email = someEmail; 
    db2.Users.Single(u => u.Email == oldEmail).Email = someEmail; 
    db1.SaveChanges(); 
    db2.SaveChanges(); //what if this fails? 
} 

所以,嘗試1:

using(var db1 = new Db1Context()) 
using(var db2 = new Db2Context()) 
using(var txs = new TransactionScope()) 
{ 
    db1.Users.Single(u => u.Email == oldEmail).Email = someEmail; 
    db2.Users.Single(u => u.Email == oldEmail).Email = someEmail; 
    db1.SaveChanges(); 
    db2.SaveChanges(); //what if this fails? 
    txs.Complete(); 
} 

失敗並ArgumentException和以下堆棧跟蹤:

[ArgumentException: Value does not fall within the expected range.] 
    System.Transactions.Oletx.IDtcProxyShimFactory.ConnectToProxy(String nodeName, Guid resourceManagerIdentifier, IntPtr managedIdentifier, Boolean& nodeNameMatches, UInt32& whereaboutsSize, CoTaskMemHandle& whereaboutsBuffer, IResourceManagerShim& resourceManagerShim) +0 
    System.Transactions.Oletx.DtcTransactionManager.Initialize() +155 
    System.Transactions.Oletx.DtcTransactionManager.get_ProxyShimFactory() +76 
    System.Transactions.TransactionInterop.GetOletxTransactionFromTransmitterPropigationToken(Byte[] propagationToken) +160 
    System.Transactions.TransactionStatePSPEOperation.PSPEPromote(InternalTransaction tx) +78 
...[etc...] 

由於我們瞭解的東西,這是因爲Azure does not support distributed transactions

所以,現在,相反,我們嘗試使用SqlTransactions:

using(var db1 = new Db1Context()) 
using(var db2 = new Db2Context()) 
{ 
    if(db1.Database.Connection.State == ConnectionState.Closed) 
    { 
     //transaction can only work on open connection 
     db1.Database.Connection.Open(); 
    } 
    using(var tx = db1.Database.Connection.BeginTransaction()) 
    { 
     //ArgumentException on next line 
     db1.Users.Single(u => u.Email == oldEmail).Email = someEmail; 
     db2.Users.Single(u => u.Email == oldEmail).Email = someEmail; 
     db1.SaveChanges(); 
     db2.SaveChanges(); //what if this fails? 
    } 
} 

這失敗的錯誤:

所以

ArgumentException: "EntityConnection can only be constructed with a closed DbConnection."

我們怎樣才能做到這一點?

回答

0

簡而言之,你不能。你需要實現2PC來支持這個。聽起來像Azure有一些非常嚴重的限制。

相關問題