[C#] 排除無須納入交易的查詢,避免產生不必要的分散式交易 (Distributed Transaction)

當不小心啟用分散式交易機制時,且環境設定不允許時,就會產生【已停用分散式交易管理員 (MSDTC) 的網路存取。請使用元件服務系統管理工具啟用 DTC,以使用 MSDTC 安全性設定中的網路存取】錯誤訊息,此時可以透過 new TransactionScope(TransactionScopeOption.Suppress) 排除不需要納入交易的部分,避免分散交易的情境產生。

前言


當操作不同 DB 伺服器且需要在同一個交易下完成,就需要使用分散式交易(Distributed Transaction)來完成;在微軟平台上 MSDTC (Distributed Transaction Coordinator) 是用來協調不同 DB 在單一交易下完成所有行為,但有時候我們不是真的需要這個功能,而是不小心啟用這個機制,且環境設定不允許時,就會產生【已停用分散式交易管理員 (MSDTC) 的網路存取。請使用元件服務系統管理工具啟用 DTC,以使用 MSDTC 安全性設定中的網路存取】錯誤訊息,而這時候要怎樣來排除呢? 請看以下實際的例子。

 

實例


目前系統使用兩台 DB 做分流,一台 read / write 都可以,另外一台 read only 做資料查詢使用;當執行功能時,需對資料庫進行一連串的資料異動行為 (connect to read / write db),同時需要取出相關資料做參考 (connect to read only db),且為了確保所有異動在同一個交易完成,會將所有邏輯包在 transaction scope 中。

 

發生錯誤


程式執行下去就報錯,錯誤訊息表示目前伺服器的設定並未啟用 DTC 功能,因此若使用到分散式交易的機制就會產生該錯誤。

System.Transactions.TransactionManagerCommunicationException: 已停用分散式交易管理員 (MSDTC) 的網路存取。請使用元件服務系統管理工具啟用 DTC,以使用 MSDTC 安全性設定中的網路存取。 ---> System.Runtime.InteropServices.COMException: 交易管理員已經停用了對遠端/網路交易的支援。 (發生例外狀況於 HRESULT: 0x8004D024)

 

錯誤排除


面對此案例來說,由於連線到 read only DB 所做的行為本來就不需要列入 transaction 中 (不對資料進行異動,且跟此次交易異動行為無關),但偏偏該行為卻又穿插在各個異動行為中,這時就可以透過 TransactionScopeOption.Suppress 參數將無須納入交易的部分再用 TransactionScop 包起來,避免分散交易的情境產生。示意代碼如下。

 

參考資訊


.NET分散式交易程式開發FAQ

 


希望此篇文章可以幫助到需要的人

若內容有誤或有其他建議請不吝留言給筆者喔 !