挖掘使用ADO.NET分布式事務登記
ADO.NET經過長時間的發展,很多用戶都很了解ADO.NET分布式事務了,這里我發表一下個人理解,和大家討論討論。事務是一組相關的任務,作為獨立于其他任務的獨立單元成功(提交)或失敗(中止)。分布式事務是影響多個資源的事務。要提交分布式事務,所有參與者都必須保證對數據的任何更改是永久的。不論系統崩潰或是發生其他無法預料的事件,更改都必須是持久的。即使只有一個參與者無法保證這一點,整個事務也將失敗,在事務范圍內對數據的任何更改均將回滾。如果 DataReader 在事務處于活動狀態時啟動,此時若嘗試提交或回滾事務,將會引發異常。
使用 System.Transactions
在 .NET Framework 中,分布式事務通過 System.Transactions 命名空間中的 API 進行管理。如果涉及多個永久資源管理器,System.Transactions API 會將分布式事務處理委托給事務監視器,例如 Microsoft 分布式事務協調程序 (MS DTC)。有關更多信息,請參見事務基礎知識。
ADO.NET 2.0 引入了對使用 EnlistTransaction 方法在分布式事務中進行登記的支持,該方法會登記 Transaction 實例中的連接。在以前版本的 ADO.NET 中,分布式事務中的顯式登記使用連接的 EnlistDistributedTransaction 方法執行,以登記 ITransaction 實例中的連接,為了向后兼容,也支持該方法。有關企業服務事務的更多信息,請參見 與企業服務和 COM+ 事務的互操作性。
在對 SQL Server 2005 數據庫使用 SQL Server .NET Framework 提供程序提供的 System.Transactions 事務時,將自動使用輕型 Transaction。該事務可以根據需要提升為完全分布式事務。有關更多信息,請參見SQL Server 的 System.Transactions 集成 (ADO.NET)。默認情況下,Oracle 數據庫可以同時參與的分布式事務的最大數目設置為 10。第 10 個事務之后,連接到 Oracle 數據庫時將會引發異常。Oracle 不支持分布式事務內的 DDL。
自動在ADO.NET分布式事務中登記
自動登記是將 ADO.NET 連接與 System.Transactions 集成的默認(和首選)方法。如果連接對象確定事務處于活動狀態,用 System.Transaction 術語來說是指 Transaction.Current 不為 Null,則連接對象會自動在現有分布式事務中登記。自動事務登記在連接打開時進行。之后,即使在事務范圍內執行命令,也不會進行自動事務登記??梢栽诂F有事務中禁用自動登記,方法是將 Enlist=false 指定為 ConnectionString 的連接字符串參數,或將 OLE DB Services=-7 指定為 ConnectionString 的連接字符串參數。有關 Oracle 和 ODBC 連接字符串參數的更多信息,請參見 ConnectionString 和 ConnectionString。
手動在ADO.NET分布式事務中登記
如果禁用了自動登記或者您需要登記在連接打開后啟動的事務,則可以使用所用提供程序的 DbConnection 對象的 EnlistTransaction 方法,在現有分布式事務中登記。在現有分布式事務中登記可以確保當提交或回滾了事務時,也提交或回滾對數據源所做作的代碼修改。
在分布式事務中登記尤其適用于為業務對象建立池連接。如果業務對象使用打開的連接建立池連接,自動事務登記只有在該連接打開時才會進行。如果使用池中的業務對象執行多個事務,則該對象的打開連接不自動登記在新啟動的事務中。在這種情況下,可以對該連接禁用自動事務登記,并使用 EnlistTransaction 在事務中登記連接。
EnlistTransaction 使用單個 Transaction 類型的參數,該參數引用現有的事務。在調用連接的 EnlistTransaction 方法之后,所有使用該連接在數據源上進行的修改均將加入事務中。傳遞空值將取消該連接在當前分布式事務登記中的登記。注意,在調用 EnlistTransaction 之前連接必須打開。在某個事務中顯式登記了連接之后,在該事務完成之前,連接將無法取消登記或在另一個事務中登記。
#T#如果連接已使用連接的 BeginTransaction 方法開始了某個事務,EnlistTransaction 將引發異常。但是,如果事務是在數據源上開始的本地事務(例如使用 SqlCommand 顯式執行 BEGIN TRANSACTION 語句),EnlistTransaction 將回滾該本地事務并根據請求在現有分布式事務中登記。您不會接收本地事務已回滾的通知,必須管理任何未使用 BeginTransaction 開始的本地事務。如果您在 SQL Server 2005 中使用用于 SQL Server 的 .NET Framework 數據提供程序 (SqlClient),那么在嘗試登記時將會引發異常。所有其他情況將無法發現。