WebLogic JTA プログラマーズ ガイド
![]() |
![]() |
![]() |
![]() |
外部のサードパーティのシステムは、WebLogic Server トランザクション マネージャに javax.transaction.xa.XAResource
実装を登録することによって、WebLogic Server トランザクション マネージャが調整する分散トランザクションに参加できます。WebLogic Server トランザクション マネージャは、2 フェーズ コミット (2PC) プロトコルの一部として XAResource を駆動します。これは、トランザクションのエクスポートと呼ばれます。
サードパーティ トランザクション マネージャが XAResource
インタフェースを実装している場合、トランザクションをエクスポートすることによって、サードパーティ トランザクション マネージャと WebLogic Server トランザクション マネージャを統合できます。エクスポートしたトランザクションによって、サードパーティ トランザクション マネージャは、WebLogic Server トランザクション マネージャの従属トランザクション マネージャとして機能できます。
WebLogic Server も、サードパーティ システム (外部トランザクション マネージャとも呼ばれる) が調整する分散トランザクションに参加できます。WebLogic Server の処理は、外部トランザクションの処理の一部として行われます。サードパーティ トランザクション マネージャは、コミット処理の一部として WebLogic Server のトランザクション マネージャを駆動します。これは、トランザクションのインポートと呼ばれます。
トランザクションにおけるサードパーティ システムの調整 (トランザクションのエクスポート) の詳細については、以下の節で説明します。サードパーティ システムが調整するトランザクションへの参加 (トランザクションのインポート) の詳細については、「サードパーティ トランザクション マネージャで管理されるトランザクションへの参加」を参照してください。WebLogic Server IIOP、WebLogic Tuxedo Connector (WTC) ゲートウェイ、および BEA Java Adapter for Mainframe (JAM) ゲートウェイでは、これらの章で説明しているメカニズムと同じメカニズムを内部的に使用して、WebLogic Server でのトランザクションのインポートおよびエクスポートを行います。
以下の節では、サードパーティ システムをコンフィグレーションして、WebLogic Server トランザクション マネージャが調整するトランザクションに参加する方法について説明します。
WebLogic Server トランザクション マネージャが調整する分散トランザクションに参加するには、サードパーティのシステムで javax.transaction.xa.XAResource
インタフェースを実装し、その XAResource
オブジェクトを WebLogic Server トランザクション マネージャに登録する必要があります。javax.transaction.xa.XAResource
インタフェースの実装の詳細については、「J2EE の Javadoc」(http://java.sun.com/j2ee/sdk_1.3/techdocs/api/index.html
) を参照してください。
トランザクション処理時は、サードパーティ システムの XAResource
オブジェクトを適切な各トランザクション オブジェクトに登録する必要があります。
図 8-1 には、WebLogic Server トランザクション マネージャが調整するトランザクションにサードパーティ システムが参加するプロセスを示します。
XAResource オブジェクトをトランザクションに登録する際に使用する登録モードに応じて、WebLogic Server は、適切な時に XAResource オブジェクトを自動的に解放する場合があります。登録および解放の詳細については、「トランザクションにおける XAResource の登録と解放」を参照してください。XAResource オブジェクトを WebLogic Server トランザクション マネージャで登録する詳細については、「XAResource のトランザクションへの参加の登録」を参照してください。
WebLogic Server トランザクション マネージャが調整する分散トランザクションに参加するには、サードパーティのシステムで javax.transaction.xa.XAResource
インタフェースを実装し、その XAResource
オブジェクトを WebLogic Server トランザクション マネージャに登録する必要があります。以下の処理のために登録が必要となります。
XAResource
のトランザクション ブランチ修飾子の指定。ブランチ修飾子はリソース マネージャ インスタンスのトランザクション ブランチを識別し、リソース マネージャ (RM) インスタンスが参加するすべての分散トランザクションに使用されます。各トランザクション ブランチは分散トランザクションの処理の 1 単位を表し、他のブランチとは分離しています。各トランザクション ブランチは、2 フェーズ コミット (2PC) 処理時に、準備とコミットの呼び出しのセットを 1 つだけ受け取ります。WebLogic Server トランザクション マネージャは、トランザクション ブランチ修飾子としてリソース名を使用します。 リソース マネージャ インスタンスは XAResource.isSameRM
メソッドによって定義されます。同じリソース マネージャ インスタンスに属する XAResource インスタンスは、isSameRM
に対して true を返すことになります。トランザクション ブランチの混乱を避けるために、同じリソース マネージャ インスタンスを異なるリソース名 (異なるリソース ブランチ) で登録しないでください。
javax.transaction.Transaction
オブジェクトに登録する必要があります。WebLogic Server のトランザクション マネージャでは、静的、動的、およびオブジェクト指向の 3 つの登録モードが用意されています。登録モードの詳細については、「トランザクションにおける XAResource の登録と解放」を参照してください。 XAResource
のブートストラップ。JTA 仕様では、標準の API でこれを行うことを定義していません。詳細については、JTA 1.0.1 仕様のセクション 3.4.8 を参照してください。 注意 : ここで述べる登録はプロセスごとの処理です (トランザクションごとの登録および解放とは異なります)。
XAResource 実装を WebLogic Server トランザクション マネージャに登録しないと、予期しないトランザクション ブランチ動作を引き起こす可能性があります。XA リソースが WebLogic Server 分散トランザクションに登録される前にこの登録を行わないと、WebLogic Server トランザクション マネージャはリソース名 (ブランチ修飾子) として XAResource インスタンスのクラス名を使用します。これによって、望ましくないリソース名やトランザクション ブランチの衝突が発生する可能性があります。
各リソース マネージャ インスタンスが、自身を一度だけ WebLogic Server トランザクション マネージャに登録するようにしてください。各リソース マネージャ インスタンスは登録時にリソース名によって識別されるので、回復、コミット処理、および状態モニタ時にシステムに過大なオーバーヘッドが加わり、関連する内部データ構造によって使用されるメモリが増加し、内部マップの検索効率が低下します。したがって、スケーラビリティおよびパフォーマンスの理由から、異なるトランザクション ブランチで XAResource インスタンスをむやみに登録しないようにする必要があります。
JTA XAResource では明示的なトランザクション モデルが採用されています。このモデルでは、Xid が常に XAResource メソッドで明示的に渡され、1 つのリソース マネージャ インスタンスがすべてのトランザクションを処理します。これは、暗黙的なトランザクション モデルが採用されている CORBA OTS リソースと対照的です。このモデルでは、参加対象の各トランザクションに対して異なる OTS リソース インスタンスが存在します。XAResource を設計する際は、JTA モデルを使用する必要があります。
各外部リソース マネージャ インスタンスは、サーバの起動時に WebLogic Server トランザクション マネージャに XAResource インスタンスを登録する必要があります。WebLogic Server では、起動クラスを使用して外部トランザクション マネージャを登録できます。起動クラスのコンフィグレーションの詳細については、「Administration Console オンライン ヘルプ」を参照してください。
以下の手順に従って、リソース マネージャを WebLogic Server トランザクション マネージャに登録します。
import javax.transaction.xa.XAResource;
import weblogic.transaction.TransactionManager;
import weblogic.transaction.TxHelper;
InitialContext initCtx = ... ; // 初期コンテキストに初期化する
TransactionManager tm = TxHelper.getTransactionManager();
TransactionManager tm = (TransactionManager)initCtx.lookup("weblogic.transaction.TransactionManager");
TransactionManager tm = (TransactionManager)initCtx.lookup("javax.transaction.TransactionManager");
String name = ... ; // RM インスタンスの名前
XAResource res = ... ; // RM インスタンスの XAResource インスタンス
tm.registerResource(name, res); // 標準の登録モードでリソースを登録する
さまざまな登録モードの詳細については、「トランザクションにおける XAResource の登録と解放」を参照してください。XAResource の登録時に以降に使用される登録モードを指定しますが、その登録プロセスの間に実際にリソースを登録しているわけではありません。実際の登録は、別の API を使用してトランザクションに行う必要があります (サーバ起動時ではない)。詳細については、「トランザクションにおける XAResource の登録と解放」を参照してください。
登録する各 XAResource インスタンスは、複数のトランザクションの回復およびコミット処理に並列的に使用されます。JTA 仕様バージョン 1.0.1B のセクション 3.4.6 で定義されているリソース共有を XAResource インスタンスがサポートしていることを確認してください。
注意 : 同じ XAResource の重複登録は無視されます。
リソースで新しいリクエストを受け付けなくなったら、WebLogic Server トランザクション マネージャから XAResource の登録を解除する必要があります。XAResource の登録を解除するには、次のメソッドを使用します。
tm.unregisterResource(name, res);
XAResource が分散トランザクションに参加するには、XAResource インスタンスをそのトランザクション オブジェクトに登録する必要があります。登録モードに応じて、異なる処理を実行する必要がある場合があります。WebLogic Server トランザクション マネージャでは、以下の登録モードがサポートされています。
XAResource をトランザクション オブジェクトに登録しても、登録モードが決まるのは、リソースをトランザクションに登録する際ではなく、WebLogic Server トランザクション マネージャに XAResource を登録する際です。「XAResource のトランザクションへの参加の登録」を参照してください。
XAResource.start
および end
の呼び出しは、コストがかかる場合があります。WebLogic Server トランザクション マネージャでは、これらの呼び出しの数を最小化するために以下の最適化方法が提供されています。
WebLogic Server トランザクション マネージャは XAResource 実装が明示的な解放を行うかどうかに関わらず、XAResource が解放される以下のイベントが発生する直前までは、現在のトランザクションに登録されているすべての XAResource インスタンスの解放を常に遅延します。
WebLogic Server トランザクション マネージャではデフォルトで、TMSUSPEND
フラグが指定された XAResource.end
を呼び出すことによって XAResource を解放します。TMSUSPEND
が指定された XAResource.end
が呼び出されると、カーソルが開いたままになるデータベース管理システムもあるので、可能な限り、TMSUCCESS
を指定した XAResource.end
を呼び出して XAResource を解放するようにしてください。これを行うには、javax.transaction.xa.XAResource
の代わりに getDelistFlag
メソッドが含まれる weblogic.transaction.XAResource
インタフェースを実装します。詳細については、「WebLogic Server の Javadoc」を参照してください。
標準的な登録モードでは、トランザクション オブジェクトに XAResource インスタンスを登録するのは一度だけです。また、同じトランザクションに同じブランチの XAResource インスタンスを 2 つ以上登録することもできます。WebLogic Server トランザクション マネージャでは、すべての XAResource インスタンスに対して適切な場合に XAResource.end
が呼び出されることが確保されます (以下の説明を参照)。WebLogic Server トランザクション マネージャでは、トランザクションのコミット時に、各ブランチが準備とコミットの呼び出しのセットを 1 つだけ受け取ることが確保されます。ただし、登録済みの特定の XAResource インスタンスの登録は無視されます。
標準的な登録では登録が簡素化されますが、特定のメソッド呼び出しの間の中でリソースが全くアクセスされない場合には、XAResource の不必要な登録および解放が生じる可能性もあります。
トランザクション オブジェクトに XAResource を登録するには、以下の手順に従います。
import weblogic.transaction.Transaction; // javax.transaction.Transaction の拡張
import weblogic.transaction.TransactionHelper;
Transaction tx = TransactionHelper.getTransaction();
tx.enlistResource(res);
XAResource をトランザクションに登録すると、WebLogic Server トランザクション マネージャによって、以降のすべての解放 (「トランザクションにおける XAResource の登録と解放」を参照) および再登録が管理されます。標準的な登録モードでは、WebLogic Server トランザクション マネージャは、以下の場合に同じトランザクションで XAResource を再登録します。
動的な登録モードでは、リソースの各アクセス前にトランザクション オブジェクトに XAResource インスタンスを登録する必要があります。この登録モードでは、各トランザクションに一度に登録できる XAResource インスタンスは、各トランザクション ブランチから 1 つのみです。WebLogic Server トランザクション マネージャは、最初のインスタンスが登録されてから解放されるまでの間、同じトランザクション ブランチの別の XAResource インスタンスの登録を無視します。
動的な登録では、XAResource インスタンスの登録と解放は最小限に抑えられます。
XAResource の登録は、「標準的な登録」で説明している手順と同じです。
静的な登録モードでは、トランザクション オブジェクトに XAResource インスタンスを登録する必要はありません。XAResource は、以下のイベントの際に WebLogic Server トランザクション マネージャによって、すべてのトランザクションについて暗黙的に登録されます。
注意 : 静的な登録モードを使用する前に以下の点を考慮する必要があります。
XAResource.start
および XAResource.end
を交互に呼び出すことができます。XAResource がこのような関連付けパターンをサポートするようにする必要があります。これは JTA 仕様では要求されていません。 静的な登録には、パフォーマンスに対するオーバーヘッド、アイソレーションの問題、およびトランザクション関連付け要件が厳しいという理由があるため、十分に検討した上で慎重に使用する必要があります。
コミット処理の間、WebLogic Server トランザクション マネージャは、2 フェーズ コミットを行うため、トランザクション マネージャに登録されている XAResource インスタンスか、トランザクションに現在登録されている XAResource インスタンスのいずれかを使用します。WebLogic Server トランザクション マネージャでは、各トランザクション ブランチが準備とコミットの呼び出しのセットを 1 つだけ受け取ることが確保されます。JTA 仕様バージョン 1.0.1B のセクション 3.4.6 で定義されているように、さまざまなスレッドから同時に複数のトランザクションのコミット処理を行うために、どのような XAResource インスタンスも使用できるようにする必要があります。
WebLogic Server サーバが再起動されると、WebLogic Server トランザクション マネージャは自身のトランザクション ログ (正常に準備されたが、2PC 処理の第 2 コミット フェーズを終了していない可能性のあるトランザクションのログ記録) を読み込みます。WebLogic Server トランザクション マネージャは次に、これらのトランザクションの XAResource のコミットの再試行を続行します。「XAResource のトランザクションへの参加の登録」で説明したように、WebLogic Server トランザクション マネージャのリソース登録 API の目的の 1 つは、回復を目的とした XAResource インスタンスのブートストラップのためです。サーバの再起動時に XAResource インスタンスが WebLogic Server トランザクション マネージャに登録されていることを確認する必要があります。WebLogic Server トランザクション マネージャは、有効な XAResource インスタンスが WebLogic Server トランザクション マネージャに登録されるまで、コミット呼び出しを毎分再試行します。
トランザクション コーディネータとして機能しているトランザクション マネージャがクラッシュすると、コーディネータのトランザクション ログにいくつかの不明なトランザクションが記録されないこともあります。したがって、コーディネータではサーバの再起動時に、リソース マネージャに対して XAResource.recover
を呼び出し、記録されなかった不明なトランザクションをロールバックする必要があります。コミットの再試行と同様に、WebLogic Server トランザクション マネージャは、有効な XAResource インスタンスが WebLogic Server トランザクション マネージャに登録されるまで、5 分間隔で XAResource.recover
を再試行します。
WebLogic Server トランザクション マネージャは、新しい XAResource が最初に WebLogic Server トランザクション マネージャに登録される際、トランザクション ログにそのチェックポイントを記録します。サーバの再起動時に、WebLogic Server トランザクション マネージャは、前にチェックポイントが記録され (トランザクション終了後にトランザクション ログから削除され) たすべてのリソースに対して XAResource.recover
を呼び出します。リソースがチェックポイント記録から削除されるのは、最後の PurgeResourceFromCheckpointIntervalSeconds
間隔 (デフォルトは 24 時間) にアクセスされていない場合のみです。したがって、リソース回復のオーバーヘッドを軽減するには、WebLogic Server トランザクション マネージャに登録されているリソース マネージャ インスタンスの数を最小限にする必要があります。
XAResource.recover
を実装する際は、以下に示す X/Open XA 仕様で説明されているようにフラグを使用する必要があります。
TMSTARTRSCAN
が指定された XAResource.recover
を呼び出すと、不明 Xid の最初のバッチがリソースによって返される。WebLogic Server トランザクション マネージャでは次に、回復すべき Xid がこれ以上ないことを示す null または長さゼロの配列のいずれかがリソースによって返されるまで、TMNOFLAGS
が指定された XAResource.recover
の呼び出しを繰り返し行います。前の XAResource.recover(TMSTARTRSCAN)
呼び出しですべての Xid がリソースによってすでに返されている場合、ここで null または長さゼロの配列が返されるか、前の回復スキャンがすでに終了および削除されたことを示す XAER_PROTO
が送出されることもあります。XAResource.recover
実装の一般的な問題は、フラグが無視されることや、XAResource.recover(TMNOFLAGS)
に対して常に同じ Xid のセットが返されることです。これによって、WebLogic Server トランザクション マネージャの回復が無限ループに陥り、後の失敗が引き起こされます。
TMENDRSCAN
フラグが指定された XAResource.recover
を呼び出すと、回復スキャンが終了する。追加の Xid がリソースによって返される場合があります。 注意 : すでに正常に終了しているトランザクションが、サーバの再起動時に再コミットされることがあります。これは、WebLogic Server のトランザクション ログの最適化によって起こります。WebLogic Server のトランザクション マネージャはトランザクション ログ ファイルから個々のログ記録を削除することはありませんが、特定のログ ファイルのすべてのトランザクションが正常に終了するまで待機してからすべてのファイルを削除します。この結果、サーバの再起動時に、特定のログ ファイルからのトランザクションの読み込みのいくつかが、すでに正常に終了している場合があります。
問題のある XAResource に対してサーバ スレッドを失わないように、WebLogic Server JTA には内部リソース状態モニタのメカニズムがあります。リソースがアクティブであると見なされるのは、保留中のリクエストが存在しない場合、または XAResource の保留中のリクエストの結果が XAER_RMFAIL
ではない場合です。XAResource が 2 分以内にアクティブにならない場合、WebLogic Server トランザクション マネージャは XAResource を応答なしと宣言します。XAResource に対する新たなリクエストは拒否され、XAER_RMFAIL
XAException
が送出されます。
2 分という間隔は、maxXACallMillis
JTAMBean 属性を介してコンフィグレーションできます。これは Administration Console ではエクスポーズされていません。maxXACallMillis
は、config.xml
ファイル内でコンフィグレーションできます。次に例を示します。
<Domain>
....
<JTA
MaxXACallMillis="240000"
/>
....
</Domain>
WebLogic Server トランザクション マネージャから通知を受信し、リソースが応答なしと宣言されようとしている際に、本当に応答なしかどうかを WebLogic Server トランザクション マネージャに通知するには、weblogic.transaction.XAResource
(javax.transaction.xa.XAResource
を拡張) を実装し、これをトランザクション マネージャに登録します。トランザクション マネージャは、XAResource が利用できないことを宣言しようとする際に、その detectUnavailable
メソッドを呼び出します。XAResource から true
が返されると、利用できないと宣言されることはありません。XAResource が本当に利用できない場合には、この機会にクリーンアップおよびトランザクション マネージャへの再登録を行うこともできます。詳細については、『weblogic.transaction.XAResource
』 の 「WebLogic Server の Javadoc」 を参照してください。
WebLogic Server トランザクション マネージャに直接登録するほかに、J2EE コネクタ アーキテクチャのリソース アダプタ インタフェースを実装することもできます。リソース アダプタをデプロイする際、リソース マネージャの XAResource は、WebLogic Server J2EE コンテナによって WebLogic Server トランザクション マネージャに自動的に登録されます。
詳細については、『WebLogic J2EE コネクタ アーキテクチャ』を参照してください。
以下の節では、WebLogic Server トランザクション マネージャでのトランザクションのエクスポートとインポートのヒントについて説明します。
WebLogic Server トランザクション マネージャは、ゲートウェイなどのシステム アプリケーションで共有されるようにトランザクション ログをエクスポーズします。これによって、高速ロギングのために WebLogic Server トランザクション マネージャの一括 (バッチ) 処理のトランザクション ログ最適化をシステム アプリケーションで利用できます。トランザクション ログ記録は適時に解放することが重要となります (WebLogic Server トランザクション マネージャは、トランザクション ログ ファイル内のすべての記録が解放された場合にのみトランザクション ログ ファイルを削除します)。これを行わないと、トランザクション ログ ファイルが多数作成され、コミット済みのトランザクションの多くが再コミットされ、極端なケースでは、循環衝突やトランザクション ログ ファイルの上書きが発生する可能性があります。
WebLogic Server トランザクション マネージャは、トランザクション ログ機能インタフェース weblogic.transaction.InterposedTransactionManager
をエクスポーズしています。これはサーバ上でのみ使用でき、以下の手順で取得できます。
import weblogic.transaction.ServerTransactionManager;
import weblogic.transaction.TxHelper;
ServerTransactionManager stm = (ServerTransactionManager)TxHelper.getTransactionManager();
TransactionLogger tlog = stm.getTransactionLogger();
XAResource のログ記録は、トランザクション ログに記録されるために、weblogic.transaction.TransactionLoggable
インタフェースを実装する必要があります。weblogic.transaction.TransactionLogger
インタフェースの詳細および TransactionLogger
インタフェースの使用方法については、「WebLogic Server の Javadoc」を参照してください。
WebLogic Server JTA トランザクション オブジェクトは、ローカルおよびグローバルのプロパティに関連付けられます。グローバル プロパティは、トランザクション伝播コンテキストでサーバ間を伝播され、トランザクション ログにログ記録の一部としても保存されます。トランザクションのグローバル プロパティにアクセスするには、以下の手順に従います。
import weblogic.transaction.Transaction;
import weblogic.transaction.TransactionHelper;
Transaction tx = TransactionHelper.getTransaction(); // スレッドに関連付けられたトランザクションを取得する
tx.setProperty("foo", "fooValue");
tx.getProperty("bar");
weblogic.transaction.TxHelper クラスの詳細については、「WebLogic Server の Javadoc」を参照してください。
TxHelper.createXid(int formatId, byte[] gtrid, byte[] bqual)
メソッドを使用して Xid を作成し、たとえば、回復時に WebLogic Server トランザクション マネージャに返すことができます。
weblogic.transaction.TxHelper クラスの詳細については、「WebLogic Server の Javadoc」を参照してください。
WebLogic Server JTA トランザクション オブジェクトはブランチ修飾子は持ちません (すなわち、TxHelper.getTransaction().getXid().getBranchQualifier()
は null になります)。ブランチ修飾子は個々のリソース マネージャに固有のため、WebLogic Server トランザクション マネージャは、XAResource メソッドに渡される Xid でのみブランチ修飾子を設定します。
WebLogic Server JTA では、現在のスレッドに関連付けられたトランザクションを返すために、TxHelper.getTransaction()
API が提供されています。ただし、WebLogic Server JTA は、XAResource メソッドを呼び出す前にトランザクション コンテキストをサスペンドするので、トランザクションの識別に頼れるのは、現在のスレッドに関連付けられたトランザクションではなく、Xid 入力パラメータのみです。
接続ベースのリソース使用のシナリオについては、JTA 仕様 1.0.1B のセクション 4.1 を参照してください。そこでは、トランザクション マネージャとリソース マネージャの間の JTA 対話について説明されています。JTA 仕様は http://java.sun.com/products/jta/ で参照できます。
![]() ![]() |
![]() |
![]() |