XLAは、データベース内の特定の表に変更通知を返すとともに、それらのデータベース変更のトランザクション境界に関する情報も返します。この項では、トランザクション境界のみで更新を確認する方法について説明します。これはXLAアプリケーションで一般的な要件です。
次の例に、TTClasses/XLAプログラムの一般的なメイン・ループを示します。
TTXlaPersistConnection conn; // XLA connection
TTXlaTableList list(&conn); // tables being monitored
ttXlaUpdateDesc_t ** arry; // ptr to returned XLA recs
TTStatus stat;
int records_fetched;
// ...
loop {
// fetch the updates
// could also be conn.fetchUpdates(...);
conn.fetchUpdatesWait(&arry, MAX_RECS_TO_FETCH,
&records_fetched, ...);
// Interpret the updates
for(j=0;j < records_fetched;j++){
ttXlaUpdateDesc_t *p;
p = arry[j];
list.HandleChange(p, stat);
} // end for each record fetched
// periodically call ackUpdates()
if (some condition is reached) {
conn.ackUpdates(stat) ;
}
} // loop
HandleChange()メソッド内では、レコードがinsert/update/deleteであるかどうかに応じて、<HandleInsert()、HandleUpdate()、HandleDelete()>のいずれかがコールされます。
XLAレコードが特定のトランザクションにおける最後のレコードかどうかを示すフラグにユーザーがアクセスできるのは、HandleChange()内です。
したがって、この例のループでは、トランザクション境界に関する情報によってconn.ackUpdates()をコールする時点を変更できるように、HandleChange()メソッドがその情報をループに渡す方法はありません。
1つのトランザクションにつきレコードが数個しかない一般的な状況では、これは問題になりません。fetchUpdates()またはfetchUpdatesWait()メソッドで最大1000個のレコードを返すようXLAに要求しても、通常は数個のレコードが返されるだけです。XLAはできるだけ速くレコードを返し、データベース内で膨大な数のトランザクションが発生していても、通常はXLAレコードを一度に数個ずつ、短時間で取り出すことができます。XLAレコードを一度に数個ずつ取り出す場合は、通常、XLAによって、最後に返されるレコードが確実にトランザクション境界上のレコードになります。
つまり、XLAに1000個のレコードを要求して、XLAが15個しか返さない場合は、15番目のレコードがほぼ確実にトランザクションの終了に当たります。
XLAは、次のことを保証します。
入念なXLAアプリケーションでは、XLAレコードのバッチにおける最後のレコードにトランザクション境界があるかどうか検証し、このトランザクション境界のみでackUpdates()をコールする必要があります。これは、操作に多数の行が関連する場合に特に重要です。データベースに対して挿入/更新/削除のバルク操作を実行した場合、XLAアプリケーションが1000個のレコードを要求すると、1000個のレコードすべて(または1000個未満)を受信する可能性があります。XLAを介して最後に返されるレコードには、おそらくトランザクション終了フラグが設定されていません。実際、トランザクションによって10,000個のレコードが変更された場合、トランザクション境界に達するまでに1000個のXLAレコードのブロックを最低でも10個フェッチする必要があります。
ackUpdates()は相対的に負荷の高い操作であるため、トランザクション境界ごとにackUpdates()をコールすることはお薦めしません。入念なXLAアプリケーションでは、アプリケーション、システムまたはデータベースに障害が発生した場合、システムのリカバリ後にXLAブックマークがトランザクションの先頭に置かれるよう、確実にトランザクション境界のみでこのメソッドをコールする必要があります。
HandleChange()メソッドには、HandleChange()とメインXLAループとの間で情報の受渡しを可能にする第3のパラメータがあります。例4.3と例4.4を比較してください。
この例では、ackUpdates()は、このXLAレコードのバッチがトランザクション境界にあることがdo_acknowledgeフラグによって示された場合にのみコールされます。
TTXlaPersistConnection conn; // XLA connection
TTXlaTableList list(&conn); // tables being monitored
ttXlaUpdateDesc_t ** arry; // ptr to returned XLA recs
TTStatus stat;
int records_fetched;
int do_acknowledge;
// ...
loop {
// fetch the updates
// could also be conn.fetchUpdates(...);
conn.fetchUpdatesWait(&arry, MAX_RECS_TO_FETCH,
&records_fetched, ...);
do_acknowledge = FALSE;
// Interpret the updates
for(j=0;j < records_fetched;j++){
ttXlaUpdateDesc_t *p;
p = arry[j];
list.HandleChange(p, stat, &do_acknowledge);
} // end for each record fetched
// periodically call ackUpdates()
if (do_acknowledge == TRUE
/* and some other conditions ... */ ) {
conn.ackUpdates(stat) ;
}
} // loop
XLAメイン・ループのこの変更に加え、ttXlaUpdateDesc_tを使用するようにHandleChange()メソッドを上書きする必要があります。
TTClassesデモinstall_dir/demo/ttclasses/xlademo.cpp
は、HandleChange()メソッドの書換えを示しています。このデモ・プログラムを確認および実行して、XLAのトランザクション終了フラグの監視およびそれに応じた処理の実行方法を調べてください。