![]() ![]() ![]() ![]() |
インターセプタ フレームワークは、コンシューマ側のフレームワークで、プロデューサ側と送受信されるマークアップとユーザの対話関連の WSRP メッセージを、プログラムによってインターセプトおよび変更できるようにします。このフレームワークは、実装できるインタフェースのセットを表示します。これらのインタフェースを使用して WSRP メッセージの内容を検証し、その内容に基づいて個別のアクションを実行できます。たとえば、プロデューサからコンシューマに登録エラーが返された場合に、インターセプタがそのエラーを検出して、ユーザに情報メッセージを表示したり、登録を完了するために必要な情報を自動的に返すことができます。
図 10-1 で示すように、インターセプタは、コンシューマ側で実装されます。インターセプタは、コンシューマと 1 つまたは複数のプロデューサ間の WSRP メッセージの送受信の処理をインターセプトおよび許可します。インターセプタは、(Web アプリケーション スコープの) 特定のコンシューマ Web アプリケーションと関連付けられています。いくつかのインターセプタをグループ化して、より複雑な使用例にも対応できます。
インターセプタ フレームワークは 5 つのパブリック インターセプタ インタフェースを定義します。インターセプトを扱うには、1 つまたは複数のインタフェースを実装し、wsrp-consumer-handler-config.xml
というコンフィグレーション ファイルで実装クラスを登録します。このコンフィグレーション ファイルは Web アプリケーション スコープにあり、コンシューマ Web アプリケーションの WEB-INF
ディレクトリ内に存在します。コンフィグレーション ファイルの詳細については、「インターセプタのコンフィグレーション」を参照してください。
インターセプタを効果的に扱うには、getMarkup
や performBlockingInteraction
などの基本の WSRP 処理を理解しておく必要があります。これらの処理の目的と、それらがプロキシ ポートレットのライフサイクルにどのように適合するかを理解する必要があります。「インターセプタの設計」を参照してください。
この章の残りの部分では、これらのインタフェースの使用方法と詳細な例および使用例を説明します。
コンシューマ側の開発者の場合、多くのさまざまな目的に対してインターセプタ フレームワークを使用できます。インターセプタの非常に一般的な使用例としては、次のものがあります。
この節では、インターセプタの作成に含まれる基本手順を説明します。各手順の詳細については、この章の別の節を参照してください。基本的な手順は、次のとおりです。
インターセプタを設計するとき、実行する作業の種類を最初に決定する必要があります。タスクに依存して、1 つまたは複数のインタフェースを実装できます。各インタフェースは、WSRP 操作の特定のタイプを処理するように設計されます。たとえば、フォーム データがプロデューサに送信される前に、それをインターセプトする場合は、IBlockingInteractionInterceptor の実装を選択できます。登録障害を処理中の場合、インタフェースのすべてを実装する場合もあります。
インターセプタは、次のタイプの WSRP を処理するように設計されています。これらの処理は、WSRP を使用してコンシューマとプロデューサ間で渡される SOAP メッセージでラップされます。
インターセプタを効果的に使用するには、これらの処理の目的と、それをプロキシ ポートレットのライフサイクルに関連させる方法を理解する必要があります。たとえば、performBlockingInteraction
要求は、ユーザがポートレットでフォーム データを送るときに送信されます。
ヒント : | WSRP および前のタイプの WSRP 操作の詳細については、dev2dev の Web サイトにある「インサイド WSRP」を参照してください。概要については、「連合ポータルのアーキテクチャ」を参照してください。 |
インターセプタを設計するとき、作業を遂行するのに必要なインターセプタの数についても考慮します。インターセプタのグループを作成することにより、プロデューサに複数のインターセプタを関連付けることができます。グループは、メソッドが実行される順序を管理する特定のルールに従います。詳細については、「メソッド実行の順序」を参照してください。
ヒント : | すべての要求が利用可能な同じデータを保有しているわけではないので、適切な null 条件チェックを追加して、データがない場合は適切な措置を取ることが重要です。 |
この節では、5 つのパブリック インターセプタ インタフェース、そのメソッド、メソッド戻り値、およびインタフェース メソッドにアクセス可能なコンテキスト オブジェクトについて説明します。この節では、次のトピックについて説明します。
インターセプタ メソッドは、インターセプトされた SOAP メッセージで値を入手および設定するのに使用できるコンテキスト オブジェクトを受信します。インターセプタの各タイプに対して作成されるコンテキスト オブジェクトは、それが表す WSRP 処理により異なります。たとえば、initCookie
コンテキスト オブジェクトは、handleEvents
処理に対するコンテキスト オブジェクトと同じ情報を含みません。これらのオブジェクトの詳細については、インターセプタ インタフェース用の「Javadoc」を参照してください。この節では、要求と応答コンテキスト オブジェクトがインターセプタにより作成および使用されるフローを説明します。
メッセージがプロデューサに送信される前、または受信後に、インターセプタ フレームワークはインターセプタ メソッドに渡される適切なコンテキスト オブジェクトを作成します。このオブジェクトはメッセージに関連した特定の要素をラップします。コンテキスト オブジェクトのメソッドを使用して、インターセプタはこれらの要素を検索および設定できます。たとえば、ユーザがリモート ポートレットでリンクをクリックすると、インターセプタ フレームワークは、インターセプタの preInvoke()
メソッドに渡される要求コンテキスト オブジェクトを作成します。インターセプタを通過し、場合によっては変更された後、要求オブジェクトはプロデューサに送信されるメッセージを作成するのに使用されます。同様に、インターセプタ フレームワークは入力メッセージから応答コンテキスト オブジェクトを作成し、そのオブジェクトを適切なインターセプタ メソッドに渡します。
図 10-2 に表示されているように、要求コンテキストは、登録されているインターセプタの preInvoke()
メソッドに渡されます。要求コンテキストには、ポートレットに関連する情報が含まれています。1 つまたは複数のインターセプタにより処理された後、インターセプタ フレームワークはメッセージを作成します。このメッセージには preInvoke()
メソッドによる変更が含まれます。
同様に、図 10-3 に示されているように、入力メッセージから作成される応答コンテキスト オブジェクトは、応答を生成したプロデューサに関連するインターセプタの postInvoke()
メソッドに渡されます。
最後に、図 10-4 に示すように、入力エラーまたは障害メッセージが onFault()
または onIOFailure()
メソッドに渡されます。onIOFailure
の場合、応答 SOAP メッセージが生成されない場合があります。
5 つのパブリック インターセプタ インタフェースは、表 10-1 に要約されています。これらのインタフェースは、com.bea.wsrp.consumer.interceptor
パッケージ内にあります。Javadoc は、これらのインタフェースで利用可能です。
getRenderDependencies 要求または応答のインターセプトを許可する。依存関係の表示には、JavaScript ファイルなどのカスケーディング スタイルシート (CSS) ファイルとスクリプトが含まれ、それに基づいてポートレットの正しい表示が行われる。依存関係の表示機能の詳細については、『ポートレット開発ガイド』の「ポートレットの外観と機能」を参照してください。
|
各インターセプタ インタフェースには、同じ 4 つのメソッドが含まれます。表 10-2 は、インターセプタ メソッドおよび各メソッドがいつ呼び出されるかを要約しています。各メソッドに対する可能な戻り値は、「インターセプタ メソッド戻り値」で説明されています。
ヒント : | 次表は概要のみで、メソッド パラメータや戻り値は含んでいません。特定のメソッド署名はメソッドが使用されるインタフェースに依存します。各メソッドとそのパラメータの詳しい説明については、「Javadoc」を参照してください。 |
次表は、4 つのインターセプタ メソッドのそれぞれに対して見込まれる戻り値を表示しています。
戻り値の詳細については、「リターン ステータスの実行順序への影響」を参照してください。
インターセプタは、Web アプリケーション スコープのコンフィグレーション ファイルである wsrp-consumer-handler-config.xml
でコンフィグレーションされます。このコンフィグレーション ファイルには、interceptor
と interceptor-group
の 2 つのエントリが必要です。これらのエントリの両方が、コンフィグレーション ファイルに存在する必要があります。
<interceptor>
要素は、完全修飾インターセプタ クラス名を指定し、任意の、ユニークな名前を提供します。インターセプタ クラスは、Web アプリケーションのクラス パスまたは、システム定義クラスパスなどの別のアクセス可能なクラスパス内にも存在しなければなりません。<interceptor>
要素により指定される各インターセプタは、グループ内で参照される必要があるので、少なくとも 1 つの <interceptor-group>
をコンフィグレーションする必要があります。
<interceptor>
要素には、次の要素が含まれます。
<interceptor-group>
要素には、次の要素が含まれます。
グループおよびグループ内のメソッドが呼び出される順序の詳細については、「メソッド実行の順序」を参照してください。
コード リスト 10-1 は、2 つのインターセプタと 1 つのグループを含む単純なコンフィグレーションを示しています。
<interceptor>
<name>AutoRegisteringInterceptor</name>
<class-name>myInterceptors.AutoRegistrationInterceptor</class-name>
</interceptor>
<interceptor>
<name>ErrorMessageCustomizer</name>
<class-name>myInterceptors.ErrorMessageCustomizer</class-name>
</interceptor>
<interceptor-group>
<name>Group_1</name>
<producer-handle>MyProducer</producer-handle>
<interceptor-name>AutoRegistrationInterceptor</interceptor-name>
<interceptor-name>ErrorMessageCustomizer</interceptor-name>
</interceptor-group>
この節では、インターセプタおよびインターセプタのグループでメソッドの実行の順序に影響する要因について説明します。
インターセプタ グループは、メソッドがきちんと定義された順序に呼び出されるインターセプタの集合です。グループは、特定のプロデューサに関連付けることも、どのプロデューサにも関連付けないことも可能です。単一のプロデューサに関連付けられる場合、グループ内のインターセプタは、コンシューマとその特定のプロデューサ間で要求と応答が発生する場合のみ呼び出されます。どのプロデューサもグループに関連付けられない場合、グループのインターセプタは、コンシューマとそれに関連付けられているすべてのプロデューサ間に通信が発生するときに呼び出されます。グループのコンフィグレーションの詳細については、「インターセプタのコンフィグレーション」を参照してください。
この節では、すべてのメソッドが CONTINUE_CHAIN
のステータス値を返す場合に、インターセプタ メソッドが呼び出される順序について説明します。
すべてのインターセプタには、preInvoke()
、postInvoke()
、onFault()
、および onIOFailure()
の 4 つのメソッドが含まれています。インターセプタ チェーンでは、preInvoke()
メソッドのすべてが実行され、次に postInvoke()
メソッド、onFault()
メソッド、最後に onIOFailure()
メソッドが実行されます。
図 10-5 は、インターセプタ チェーン内のメソッドが次のチェーン定義について呼び出される順序を示しています。
<interceptor-chain>
<name>Chain-A</name>
<producer-handle>myProducer</producer-handle>
<interceptor-name>Interceptor2</interceptor-name>
<interceptor-name>Interceptor3</interceptor-name>
<interceptor-name>Interceptor3</interceptor-name>
<interceptor-name>Interceptor4</interceptor-name>
</interceptor-chain>
この図では、すべてのメソッドが CONTINUE_CHAIN
ステータスを返すと仮定しています。チェーン コンフィグレーションにインターセプタが表示される順序で、すべての preInvoke()
メソッドが最初に呼び出され、次に postInvoke()
メソッドが逆の順序で呼び出されます。すべての postInvoke()
メソッドが呼び出された後に、onFault()
メソッドが 図 10-5 に示されている順序で呼び出されます。最後に、onIOFailure()
メソッドが、図 10-5 に示される順序で呼び出されます。onFault()
または onIOFailure()
が呼び出されると、次に postInvoke()
は呼び出されません。
ヒント : | 特定のプロデューサに関連付けられているか、またはどの特定のプロデューサにも関連付けられていないインターセプタを、コンフィグレーション ファイル内に定義できます。関連付けられていないインターセプタには、それと一緒に定義されている <producer-handle> 要素はありません。関連付けられていないインターセプタは常に、すべてのプロデューサ トランザクションについて、特定のプロデューサに関連付けられているインターセプタが呼び出される前に、最初に呼び出されます。関連付けられていないインターセプタは、コンフィグレーション ファイルに表示される順序に呼び出されます。詳細については、「インターセプタのコンフィグレーション」を参照してください。 |
インターセプタ メソッドのリターン ステータスは、インターセプタ メソッドが実行される順序にも影響します。インターセプタ メソッドのチェーンについて考えることが役に立ちます。preInvoke()
チェーン、postInvoke()
チェーン、onFault()
チェーン、および onIOFailure()
チェーンの 4 つの個別のチェーンについて考えると、インターセプタ チェーンの機能方法が理解しやくすなります。このようにチェーンについて考えると、チェーンの実行に対するリターン ステータスの影響が理解しやすくなります。
表 10-7 は、インターセプタ メソッドに対して見込まれる戻り値と、それがどのようにチェーンでの実行順序に影響するかを要約しています。
注意 : | ABORT_CHAIN または SKIP_REQUEST_ABORT_CHAIN が preInvoke() から返される場合、postInvoke() 段階の間、インターセプタのすべては逆の順序で呼び出されます。 |
インターセプタ実装クラスの新しいインスタンスは、preInvoke()
を呼び出す前に、すべてのメッセージに対して作成されます。この同じインスタンスは、postInvoke()
、onFault()
、および onIOFailure()
を呼び出すのに再利用されます。これにより、要求の範囲内でインスタンス変数を設定および使用できます。特定のインスタンスについて、すべてのメソッドが 1 回呼び出されますが、RETRY
ステータスが、onFault()
または onIOFailure()
のいずれかにより返される場合、preInvoke()
および postInvoke()
は、もう一度呼び出すことができます。許可される再試行は、1 つのメッセージにつき 1 回だけです。
この節では、インターセプタ チェーンにおけるメソッド実行のフローを示すいくつかの例を説明します。これらの例で参照されるインターセプタの戻り値の詳細については、表 10-7 を参照してください。
図 10-6 は、preInvoke()
メソッドがチェーンで呼び出されるときのインターセプタ チェーンでのフローを示しています。ABORT_CHAIN
のステータスが返されるとき、メッセージはプロデューサにすぐに返されます。チェーン内で後続のインターセプタの preInvoke()
メソッドは呼び出されません。
図 10-7 は、preInvoke()
メソッドがチェーンで呼び出されるときのインターセプタ チェーンでのフローのもう 1 つの例を示しています。SKIP_REQUEST_ABORT_CHAIN
のステータスが返されるとき、プロデューサにはメッセージが送信されません。チェーン内で後続のインターセプタの preInvoke()
メソッドは呼び出されません。
図 10-8 は、onFault()
メソッドがチェーンで呼び出されるときのインターセプタ チェーンでのフローを示しています。RETRY
のステータスが戻されると、エラーの原因となった同じメッセージが、インターセプタにより挿入される可能性のある修正と共に、プロデューサに戻されます。チェーン内で後続のインターセプタの onFault()
メソッドは呼び出されません。許可される再試行は、1 回だけです。同じエラーが返される場合、インターセプタ フレームワークはそのエラーがインターセプタによって処理されると判断し、HANDLED
ステータスが返されます。
図 10-9 は、onIOFailure()
メソッドがチェーンで呼び出されるときのインターセプタ チェーンでのフローを示しています。この場合、何のメッセージもプロデューサに戻されないので、フレームワークでは、インターセプタにより障害が消滅されたと仮定します。チェーン内で後続のインターセプタの onIOFailure()
メソッドは呼び出されません。許可される再試行は、1 回だけです。2 回目の再試行は認められず、障害または例外はプロキシ ポートレットに渡されます。同じエラーが返される場合、インターセプタ フレームワークはそのエラーがインターセプタによって処理されると判断し、HANDLED
ステータスが返されます。
この節では 2 つの単純なインターセプタ実装を説明します。最初は onFault()
メソッドを実装し、プロデューサに戻されるエラー メッセージを変更します。2 番目は onFault()
を実装し、ポートレットをリダイレクトして、エラー ページを表示します。
インターセプタを使用して、プロデューサから投げられた例外を取得し変更できます。コード リスト 10-3 で、onFault()
メソッドは応答から Throwable を取得します。onFault()
メソッドを設計して、例外を検討し、適切な措置を取ることができます。この場合、エラー メッセージが取得、変更され、IGetMarkupResponseContext オブジェクトに書き戻されます。リターン ステータス HANDLED
には次の効果があります。
onFault()
メソッドの呼び出しをスキップする。 import com.bea.wsrp.consumer.interceptor.IGetMarkupInterceptor;
import com.bea.wsrp.model.markup.IGetMarkupRequestContext;
import com.bea.wsrp.model.markup.IGetMarkupResponseContext;
import com.bea.wsrp.consumer.interceptor.Status;
import weblogic.xml.util.StringInputStream;
public class ErrorMessageCustomizer implements IGetMarkupInterceptor
{
public Status.PreInvoke preInvoke(IGetMarkupRequestContext requestContext)
{
return Status.PreInvoke.CONTINUE_CHAIN;
}
public Status.PostInvoke postInvoke(IGetMarkupRequestContext requestContext,
IGetMarkupResponseContext responseContext)
{
return Status.PostInvoke.CONTINUE_CHAIN;
}
public Status.OnFault onFault(IGetMarkupRequestContext requestContext,
IGetMarkupResponseContext responseContext,
Throwable t)
{
String message = "This Message is Customized by ErrorMessageCustomizer\n";
message = message + t.getMessage();
StringInputStream stringInputStream = new StringInputStream(message);
responseContext.setMarkupData(stringInputStream);
return Status.OnFault.HANDLED;
}
public Status.OnIOFailure onIOFailure(IGetMarkupRequestContext requestContext,
IGetMarkupResponseContext responseContext, Throwable t)
{
return Status.OnIOFailure.CONTINUE_CHAIN;
}
}
この例では、onFault()
メソッドが実装され、ポートレットにエラー JSP ページが含まれています。
import com.bea.wsrp.consumer.interceptor.IGetMarkupInterceptor;
import com.bea.wsrp.model.markup.IGetMarkupRequestContext;
import com.bea.wsrp.model.markup.IGetMarkupResponseContext;
import com.bea.wsrp.consumer.interceptor.Status;
import weblogic.xml.util.StringInputStream;
import myClasses.MyError;
public class DisplayErrorPage implements IGetMarkupInterceptor
{
public Status.PreInvoke preInvoke(IGetMarkupRequestContext requestContext)
{
return Status.PreInvoke.CONTINUE_CHAIN;
}
public Status.PostInvoke postInvoke(IGetMarkupRequestContext
requestContext, IGetMarkupResponseContext responseContext)
{
return Status.PostInvoke.CONTINUE_CHAIN;
}
public Status.OnFault onFault(IGetMarkupRequestContext requestContext,
IGetMarkupResponseContext responseContext,
Throwable t)
{
try
{
if (t instanceof MyError) {
responseContext.render(requestContext.getHttpServletRequest(),
requestContext.getHttpServletResponse(),
"/redirectTarget/myTarget.jsp");
} else {
responseContext.render(requestContext.getHttpServletRequest(),
requestContext.getHttpServletResponse(),
"/redirectTarget/defaultTarget.jsp");
}
}
catch (ServletException e)
{
e.printStackTrace();
}
catch (IOException e)
{
e.printStackTrace();
}
return Status.OnFault.HANDLED;
}
public Status.OnIOFailure onIOFailure(IGetMarkupRequestContext
requestContext, IGetMarkupResponseContext
responseContext, Throwable t)
{
return Status.OnIOFailure.CONTINUE_CHAIN;
}
}
![]() ![]() ![]() |