任何使用核心交易管理員 (KTM) 和通用記錄檔系統 (CLFS) 的交易處理系統 (TPS) 都應該包含下列重要元件:
交易管理員 (KTM)
KTM 會追蹤每個交易的狀態,並在系統損毀之後協調復原作業。
一或多個 資源管理員
您提供的資源管理員會管理與每個交易相關聯的資料。
一或多個 CLFS 日誌流
交易管理員和資源管理員會使用 CLFS 記錄串流來記錄可用來認可、回滾或復原交易的資訊。
一或多個 交易式用戶端
一般而言,TPS 的每個交易用戶端都可以建立交易、在交易內容內對資料執行作業,然後起始交易的認可或復原作業。
本文會向您介紹具有一個資源管理員的 簡單 TPS 、包含 多個資源管理員的更複雜的 TPS,以及 一些其他 TPS 案例。
使用 KTM 一節提供如何使用 KTM 建立 TPS 元件的詳細資訊。
簡單的 TPS
簡單的 TPS 可能包含 KTM、一個資源管理員和 CLFS。 交易式用戶端可以透過資源管理員提供的介面與資源管理員通訊。
例如,假設您想要建立資料庫管理系統。 您想要系統的用戶端藉由開啟資料庫物件的控制碼、對物件執行讀取和寫入作業,然後關閉物件控制碼來存取資料庫。
現在假設您希望以原子方式進行讀取和寫入操作集合,以便系統的其他使用者只能看到最終結果。 您可以設計 TPS 來達成該目標,讓用戶端能夠將資料庫作業集繫結至交易。
您的系統應該包含一個資源管理器,用於管理資料庫中的資料,以回應來自用戶端的讀取和寫入請求。 此資源管理員可以匯出應用程式設計介面 (API),讓用戶端能夠將交易與一組讀取和寫入作業相關聯。
當您載入資源管理器時,它必須透過呼叫 ZwCreateTransactionManager 和 ZwCreateResourceManager 來向 KTM 註冊自身。 然後,資源管理員可以參與交易。
您可能想要資源管理程式支援一組函式,讓用戶端能夠建立資料物件、讀取和寫入與資料物件相關聯的資料,以及關閉資料物件。 下列虛擬程式碼顯示來自用戶端的範例程式碼序列。
CreateDataObject (IN TransactionID, OUT DataHandle);
ReadData (IN DataHandle, OUT Data);
WriteData (IN DataHandle, IN Data);
WriteData (IN DataHandle, IN Data);
WriteData (IN DataHandle, IN Data);
CloseDataObject (IN DataHandle);
用戶端可以呼叫資源管理員的 CreateDataObject 常式之前,用戶端必須呼叫 KTM 的 ZwCreateTransaction 常式來建立交易物件,並呼叫 ZwQueryInformationTransaction 來取得交易物件的識別碼。
當用戶端呼叫資源管理員的 CreateDataObject 常式時,用戶端會將交易物件的識別碼傳遞至資源管理員。 資源管理員可以呼叫 ZwOpenTransaction 來取得交易物件的控制碼,然後可以呼叫 ZwCreateEnlistment 來註冊其參與交易。
此時,用戶端可以開始對資料物件執行作業。 因為用戶端在建立資料物件時提供了交易識別碼,所以資源管理員可以將所有讀取和寫入作業指派給交易。
您的資源管理員必須記錄用戶端指定之資料作業的所有結果,而不會使結果永久化。 一般而言,資源管理員會使用 CLFS 在交易記錄資料流程中記錄作業結果。
當用戶端完成呼叫資源管理員以執行交易式作業時,它會呼叫 KTM 的 ZwCommitTransaction 常式。 此時,KTM 會通知 資源管理員,它應該讓作業永久化。 然後,資源管理程式會將作業結果從日誌串流移至資料的永久儲存媒體。 最後,資源管理員會呼叫 ZwCommitComplete ,以通知 KTM 認可作業已完成。
如果您的資源管理員報告用戶端其中一個呼叫 ReadData 或 WriteData 的錯誤,會發生什麼情況? 用戶端可以呼叫 ZwRollbackTransaction 來復原交易。 由於該呼叫,KTM 會通知資源管理員它應該將數據還原為其原始狀態。 然後,用戶端可以為相同的作業建立新交易,也可以選擇不繼續。
下列虛擬程式碼顯示用戶端交易作業更詳細順序的範例。
ZwCreateTransaction (&TransactionHandle, ...);
ZwQueryInformationTransaction (TransactionHandle, ...);
CreateDataObject (TransactionID, &DataHandle);
Status = ReadData (DataHandle, &Data1);
if (Status == Error) goto ErrorRollback;
Status = WriteData (DataHandle, Data2);
if (Status == Error) goto ErrorRollback;
Status = WriteData (DataHandle, Data3);
if (Status == Error) goto ErrorRollback;
Status = WriteData (DataHandle, Data4);
if (Status == Error) goto ErrorRollback;
ZwCommitTransaction (TransactionHandle, ...);
goto Leave;
ErrorRollback:
ZwRollbackTransaction (TransactionHandle, ...);
Leave:
ZwClose (TransactionHandle);
return;
如果系統在交易建立後但在提交或復原之前崩潰,會發生什麼情況? 每次載入資源管理員時,它都應該呼叫 ZwRecoverTransactionManager 和 ZwRecoverResourceManager。 呼叫 ZwRecoverTransactionManager 會導致 KTM 開啟其記錄資料流程,並讀取交易歷程記錄。 呼叫 ZwRecoverResourceManager 會導致 KTM 通知資源管理員在損毀之前進行中的任何已登記交易,以及資源管理員因此必須復原哪些交易。
如果交易用戶端在當機之前呼叫了ZwCommitTransaction進行交易,並開始處理該交易的認可作業,則資源管理員必須能夠將交易的狀態還原至緊接當機之前的點。 如果用戶端在當機之前尚未準備好認可交易,資源管理員可以捨棄資料並復原交易。
如需如何撰寫交易式用戶端的詳細資訊,請參閱 建立交易式用戶端。
如需如何撰寫資源管理員的詳細資訊,請參閱 建立資源管理員。
TPS 中的多個資源管理員
現在假設您的 TPS 可讓用戶端在單一交易內修改兩個不同資料庫中的資訊,因此只有在兩個資料庫的修改成功時,交易才會成功。
在此情況下,您的 TPS 可以有兩個資源管理員,每個資料庫一個。 每個資源管理員都可以匯出用戶端可用來存取資源管理員資料庫的 API。
下列虛擬程式碼顯示用戶端如何建立單一交易,其中包含兩個資源管理員支援的兩個資料庫上的作業。
在此範例中,用戶端會從第一個資料庫讀取資料,並將它寫入第二個資料庫。 然後,用戶端從第二個資料庫讀取資料,並將其寫入第一個資料庫。 (第一個資源管理程式會匯出以 Rm1 開頭的函式,第二個資源管理程式會匯出以 Rm2 開頭的函式。
ZwCreateTransaction (&TransactionHandle, ...);
ZwQueryInformationTransaction (TransactionHandle, ...);
Rm1CreateDataObject (TransactionID, &Rm1DataHandle);
Rm2CreateDataObject (TransactionID, &Rm2DataHandle);
Status = Rm1ReadData (Rm1DataHandle, &Rm1Data);
if (Status == Error) goto ErrorRollback;
Status = Rm2WriteData (Rm2DataHandle, Rm1Data);
if (Status == Error) goto ErrorRollback;
Status = Rm2ReadData (Rm2DataHandle, &Rm2Data);
if (Status == Error) goto ErrorRollback;
Status = Rm1WriteData (Rm1DataHandle, Rm2Data);
if (Status == Error) goto ErrorRollback;
ZwCommitTransaction (TransactionHandle, ...);
goto Leave;
ErrorRollback:
ZwRollbackTransaction (TransactionHandle, ...);
Leave:
ZwClose (TransactionHandle);
return;
因為用戶端會將相同的交易識別碼傳遞至兩個資源管理員,所以這兩個資源管理員都可以呼叫 ZwOpenTransaction 和 ZwCreateEnlistment 來登記交易。 當用戶端最終呼叫 ZwCommitTransaction 時,KTM 會通知 每個資源管理員,管理員應該讓作業永久化,而每個資源管理員會在完成時呼叫 ZwCommitComplete 。
其他 TPS 案例
KTM 支援其他 TPS 情境。 例如,下列案例描述 TPS 可能包含的元件:
一個管理多個資料庫的資源管理員。
資源管理員的 API 可讓用戶端一次開啟和存取多個資料庫,而且用戶端可以在單一交易中合併對多個資料庫的存取。
一個資源管理員提供用戶端呼叫的 API,其他資源管理員提供第一個資源管理員呼叫的 API。
用戶端只會與第一個資源管理員通訊。 當該資源管理員處理來自用戶端的要求時,它可以視需要存取其他資源管理員,以處理用戶端的要求。 例如,資源管理員會管理用戶端可存取的資料庫,該資料庫需要從用戶端無法存取的第二個資源管理員進行備份或資料驗證作業。
不使用 KTM 的現有客戶端與資源管理員,與使用 KTM 的另一組資源管理員進行整合。
在此情況下,您通常必須修改現有的資源管理員,讓它成為與 KTM 通訊的 上級交易管理員 。