Oracle® Fusion Middleware

Oracle WebLogic Server 12.1.3 JAX-WS Webサービスの開発

12c (12.1.3)

E57563-04(原本部品番号:E47706-04)

2015年8月

このドキュメントでは、ソフトウェア開発者を対象に、WebLogic Server 12.1.3のJava API for XML-based Web services (JAX-WS)を使用してJava EE Webサービスを開発する方法について説明します。

Oracle Fusion Middleware Oracle WebLogic Server 12.1.3 JAX-WS Webサービスの開発, 12c (12.1.3)

E57563-04

Copyright © 2013, 2015, Oracle and/or its affiliates.All rights reserved.

このソフトウェアおよび関連ドキュメントの使用と開示は、ライセンス契約の制約条件に従うものとし、知的財産に関する法律により保護されています。ライセンス契約で明示的に許諾されている場合もしくは法律によって認められている場合を除き、形式、手段に関係なく、いかなる部分も使用、複写、複製、翻訳、放送、修正、ライセンス供与、送信、配布、発表、実行、公開または表示することはできません。このソフトウェアのリバース・エンジニアリング、逆アセンブル、逆コンパイルは互換性のために法律によって規定されている場合を除き、禁止されています。

ここに記載された情報は予告なしに変更される場合があります。また、誤りが無いことの保証はいたしかねます。誤りを見つけた場合は、オラクル社までご連絡ください。

このソフトウェアまたは関連ドキュメントを、米国政府機関もしくは米国政府機関に代わってこのソフトウェアまたは関連ドキュメントをライセンスされた者に提供する場合は、次の通知が適用されます。

U.S. GOVERNMENT END USERS: Oracle programs, including any operating system, integrated software, any programs installed on the hardware, and/or documentation, delivered to U.S. Government end users are "commercial computer software" pursuant to the applicable Federal Acquisition Regulation and agency-specific supplemental regulations. As such, use, duplication, disclosure, modification, and adaptation of the programs, including any operating system, integrated software, any programs installed on the hardware, and/or documentation, shall be subject to license terms and license restrictions applicable to the programs. No other rights are granted to the U.S. Government.

このソフトウェアもしくはハードウェアは様々な情報管理アプリケーションでの一般的な使用のために開発されたものです。このソフトウェアもしくはハードウェアは、危険が伴うアプリケーション(人的傷害を発生させる可能性があるアプリケーションを含む)への用途を目的として開発されていません。このソフトウェアもしくはハードウェアを危険が伴うアプリケーションで使用する際、安全に使用するために、適切な安全装置、バックアップ、冗長性(redundancy)、その他の対策を講じることは使用者の責任となります。このソフトウェアもしくはハードウェアを危険が伴うアプリケーションで使用したことに起因して損害が発生しても、オラクル社およびその関連会社は一切の責任を負いかねます。

OracleおよびJavaはOracle Corporationおよびその関連企業の登録商標です。その他の名称は、それぞれの所有者の商標または登録商標です。

Intel、Intel Xeonは、Intel Corporationの商標または登録商標です。すべてのSPARCの商標はライセンスをもとに使用し、SPARC International, Inc.の商標または登録商標です。AMD、Opteron、AMDロゴ、AMD Opteronロゴは、Advanced Micro Devices, Inc.の商標または登録商標です。UNIXは、The Open Groupの登録商標です。

このソフトウェアまたはハードウェア、そしてドキュメントは、第三者のコンテンツ、製品、サービスへのアクセス、あるいはそれらに関する情報を提供することがあります。適用されるお客様とOracle Corporationとの間の契約に別段の定めがある場合を除いて、Oracle Corporationおよびその関連会社は、第三者のコンテンツ、製品、サービスに関して一切の責任を負わず、いかなる保証もいたしません。適用されるお客様とOracle Corporationとの間の契約に定めがある場合を除いて、Oracle Corporationおよびその関連会社は、第三者のコンテンツ、製品、サービスへのアクセスまたは使用によって損失、費用、あるいは損害が発生しても一切の責任を負いかねます。

目次

タイトルおよび著作権情報

はじめに

- ドキュメントのアクセシビリティについて

- 表記規則

このガイドでの新しい情報

- 12c (12.1.3)での新機能と変更された機能

- 12c (12.1.2)での新機能と変更された機能

第I部 概要

1 JAX-WS Webサービスの概要

- JAX-WS Webサービス開発の概要

- プログラミング・モデル - メタデータ・アノテーション

- 開発モデル - ボトムアップとトップダウン

- ボトムアップ・アプローチ: Javaから開始

- トップダウン・アプローチ: WSDLから開始

- JAX-WS Webサービスを実装するためのロードマップ

2 JAX-WS Webサービス開発者向けの例

第II部 基本的なJAX-WS Webサービスの開発

3 JAX-WS Webサービスの開発

- WebLogic Webサービス・プログラミング・モデルの概要

- 高度なWebサービス機能のためのドメインの構成

- 高度なWebサービス機能に必要なリソース

- 高度なWebサービス機能用にドメインを拡張するスクリプト

- 高度なWebサービス機能のための構成ウィザードを使用したドメインの構成

- Webサービス拡張テンプレートを使用したドメインの作成

- Webサービス拡張テンプレートを使用したドメインの拡張

- Webサービス拡張テンプレートを使用したドメイン拡張でのWLSTの利用

- ドメインの拡張後に追加されたリソースの更新

- WebLogic Advanced Web Services for JAX-WS拡張テンプレートを適用するときの問題に関するトラブルシューティング

- Javaから開始するWebLogic Webサービスの開発: 主な手順

- WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順

- 基本的なAnt build.xmlファイルの作成

- jwsc WebLogic WebサービスAntタスクの実行

- Webサービスの呼出しに使用されるトランスポートの指定

- WebLogic Webサービスのコンテキスト・パスの定義

- jwscの使用例

- wsdlc WebLogic WebサービスAntタスクの実行

- wsdlcで生成される途中まで作成済みのJWS実装クラス・ファイルの更新

- WebLogic Webサービスのデプロイとアンデプロイ

- wldeploy Antタスクを使用したWebサービスのデプロイ

- 管理コンソールを使用したWebサービスのデプロイ

- WebサービスのWSDLの参照

- 動的なWSDLで指定されたサーバー・アドレスの構成

- Webサービスがコールバック・サービスでなく、HTTP/Sを使用して呼び出せる場合

- Webサービスがコールバック・サービスである場合

- Webサービスがプロキシ・サーバーを使用して呼び出せる場合

- Webサービスのテスト

- WebサービスのWebLogic分割開発ディレクトリ環境への統合

4 JWSファイルのプログラミング

- JWSファイルとJWSアノテーションの概要

- JWSファイルのJava要件

- JWSファイルのプログラミング: 一般的な手順

- JWSファイルの例

- JWSファイルがWebサービスを実装することの指定(@WebServiceアノテーション)

- WebサービスとSOAPメッセージ・プロトコルのマッピングの指定(@SOAPBindingアノテーション)

- JWSメソッドをパブリック操作として公開することの指定(@WebMethodおよび@OneWayアノテーション)

- 操作のパラメータとWSDL要素のマッピングのカスタマイズ(@WebParamアノテーション)

- 操作の戻り値とWSDL要素のマッピングのカスタマイズ(@WebResultアノテーション)

- エンドポイントに使用するバインディングの指定(@BindingTypeアノテーション)

- Webサービスの実行時情報へのアクセス

- プロトコル・バインディング・コンテキストへのアクセス

- Webサービス・コンテキストへのアクセス

- MessageContextプロパティ値の使用

- ステートレスまたはシングルトン・セッションEJBを実装すべき場合

- ユーザー定義のJavaデータ型のプログラミング

- JWSファイルからの別のWebサービスの呼出し

- SOAP 1.2の使用

- XMLスキーマの検証

- サーバーでのスキーマ検証の有効化

- クライアントでのスキーマ検証の有効化

- JWSプログラミングのベスト・プラクティス

5 JAXBデータ・バインディングの使用

- JAXBを使用したデータ・バインディングの概要

- JAXBデータ・バインディング・アーティファクトの開発

- 標準データ型のマッピング

- サポートされる組込みデータ型

- 組込みデータ型のXML-to-Javaマッピング

- 組込みデータ型のJava-to-XMLマッピング

- サポートされるユーザー定義のデータ型

- サポートされるユーザー定義のXMLデータ型

- サポートされるユーザー定義のJavaデータ型

- JAXBアノテーションを使用したJava-to-XMLスキーマ・マッピングのカスタマイズ

- JAXBアノテーションの例

- フィールドおよびプロパティのデフォルト・シリアライゼーションの指定(@XmlAccessorTypeアノテーション)

- プロパティとローカル要素のマッピング(@XmlElement)

- MIMEタイプの指定(@XmlMimeTypeアノテーション)

- 最上位クラスとグローバル要素のマッピング(@XmlRootElement)

- 複数のクラスのバインディング(@XmlSeeAlso)

- 値クラスとスキーマ型のマッピング(@XmlType)

- バインディング宣言を使用したXMLスキーマ-to-Javaマッピングのカスタマイズ

- 外部バインディング宣言ファイルの作成

- JAX-WSバインディング宣言を使用した外部バインディング宣言ファイルの作成

- JAXBバインディング宣言を使用した外部バインディング宣言ファイルの作成

- バインディング宣言の埋め込み

- WSDLファイルへのJAX-WSまたはJAXBバインディング宣言の埋め込み

- XMLスキーマへのJAXBバインディング宣言の埋め込み

- JAX-WSカスタム・バインディング宣言

- JAXBカスタム・バインディング宣言

- Glassfish RI JAXBデータ・バインディングおよびJAXBプロバイダの使用

- サーバー全体レベルでのデータ・バインディングおよびJAXBプロバイダの構成

- アプリケーション・レベルでのデータ・バインディングおよびJAXBプロバイダの構成

- JAXB用Javaシステム・プロパティの構成

6 JAX-WS Webサービスの開発例

- 簡単なHelloWorld Webサービスの作成

- サンプルHelloWorldImpl.java JWSファイル

- HelloWorldImpl.javaのサンプルAntビルド・ファイル

- ユーザー定義のデータ型を使用するWebサービスの作成

- サンプルBasicStruct JavaBean

- サンプルComplexImpl.java JWSファイル

- ComplexImpl.java JWSファイルのサンプルAntビルド・ファイル

- WSDLファイルからのWebサービスの作成

- サンプルWSDLファイル

- TemperatureService_TemperaturePortImpl Java実装ファイルのサンプル

- TemperatureServiceのサンプルAntビルド・ファイル

第III部 基本的なJAX-WS Webサービス・クライアントの開発

7 JAX-WS Webサービス・クライアントを開発するためのロードマップ

8 Webサービス・クライアントの開発

- WebLogic Webサービス・クライアント開発の概要

- Java SEクライアントからのWebサービスの呼出し

- クライアントのアーティファクトを生成するためのclientgen Antタスクの使用

- Webサービスに関する情報の取得

- Webサービスを呼び出すJavaクライアント・アプリケーション・コードの記述

- クライアント・アプリケーションのコンパイルと実行

- JavaクライアントのサンプルAntビルド・ファイル

- スタンドアロンのJava SEクライアントからのWebサービスの呼出し

- 別のWebLogic WebサービスからのWebサービスの呼出し

- Webサービス・クライアントのサンプルbuild.xmlファイル

- Webサービスを呼び出すサンプルJWSファイル

- Webサービス・クライアントの構成

- @WebServiceRefアノテーションを使用したWebサービス参照の定義

- クライアントIDの管理

- ポート初期化時のクライアントIDの定義

- サーバー生成のクライアントIDのアクセス

- クライアントIDのライフサイクル

- Webサービス呼出し時のプロキシ・サーバーの使用

- ClientProxyFeature APIを使用したプロキシ・サーバーの指定

- システム・プロパティを使用したプロキシ・サーバーの指定

- Webサービスを再デプロイする際にクライアント側で考慮すべき事項

- Webサービスおよびクライアントを同一の管理対象サーバーにデプロイする場合のクライアントに関する考慮事項

9 JAX-WS Webサービス・クライアントの開発例

- JAX-WS Java SEクライアントの開発

- サンプルJavaクライアント・アプリケーション

- Javaクライアント・アプリケーションをビルドするためのサンプルAntビルド・ファイル

- WebLogic WebサービスからのWebサービスの呼出し

- サンプルClientServiceImpl.java JWSファイル

- ClientServiceをビルドするためのサンプルAntビルド・ファイル

第IV部 JAX-WS Webサービスの高度な機能の開発

10 Web Services Addressingの使用

- WS-Addressingの概要

- WebサービスでのWS-Addressingの有効化

- WebサービスでのWS-Addressingの有効化(Javaから始める場合)

- WebサービスでのWS-Addressingの有効化(WSDLから始める場合)

- Webサービス・クライアントでのWS-Addressingの有効化

- Webサービス・クライアントでのWS-Addressingの明示的な有効化

- Webサービス・クライアントでのWS-Addressingの暗黙的な有効化

- Webサービス・クライアントでのWS-Addressingの無効化

- WS-AddressingのActionプロパティの関連付け

- WS-AddressingのActionプロパティの明示的な関連付け(Javaから始める場合)

- WS-AddressingのActionプロパティの明示的な関連付け(WSDLから始める場合)

- WS-AddressingのActionプロパティの暗黙的な関連付け

- 匿名WS-Addressingの構成

11 非同期Webサービス・クライアントを開発するためのロードマップ

12 非同期クライアントの開発

- Webサービスの非同期呼出しの概要

- Webサービスを非同期に呼び出す手順

- Webサービスを非同期に呼び出すためのサーバーの構成

- Webサービスを非同期に呼び出すためのクライアント・アーティファクトの構築

- スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)

- 非同期クライアント・トランスポート機能の有効化と構成

- 非同期レスポンス・エンドポイントのアドレスの構成

- 非同期レスポンス・エンドポイントのReplyToヘッダーとFaultToヘッダーの構成

- 非同期レスポンス・エンドポイントのコンテキスト・パスの構成

- 非同期レスポンス・エンドポイントの公開

- 同期操作用の非同期クライアント・トランスポートの構成

- 非同期ハンドラ・インタフェースの開発

- レスポンスへのユーザー定義リクエスト・コンテキストの伝播

- ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)

- Webサービスでの接続作成の有効化と構成

- Webサービスの接続作成WS-Policyファイルの作成(オプション)

- 接続作成を有効にするためのJWSファイルのプログラミング

- Webサービス・クライアントでの接続作成の有効化と構成

- 接続作成メッセージ送信の有効時間の構成

- ポーリング間隔の構成

- 指数関数的バックオフの構成

- 同期メソッドのトランスポートとしての接続作成の構成

- JAX-WS参照実装の使用

- レスポンスへのリクエスト・コンテキストの伝播

- 非同期Webサービス呼出しのモニタリング

- 非同期Webサービス・メッセージングのクラスタリングの考慮事項

13 信頼性のあるWebサービスとクライアントを開発するためのロードマップ

- 信頼性のあるWebサービス・クライアントを開発するためのロードマップ

- 信頼性のあるWebサービスを開発するためのロードマップ

- ファイアウォールの背後から信頼性のあるWebサービスにアクセスする(接続を作成する)ためのロードマップ

- 信頼性のあるWebサービスを保護するためのロードマップ

14 Webサービスの信頼性のあるメッセージングの使用

- Webサービスの信頼性のあるメッセージングの概要

- WS-Policyを使用した信頼性のあるメッセージング・ポリシーのアサーションの指定

- 信頼性のあるメッセージングでサポートされるトランスポート・タイプ

- 信頼性のあるメッセージ・シーケンスのライフサイクル

- 信頼性のあるメッセージングの障害リカバリのシナリオ

- リクエストが到着する前にRM宛先がダウンする

- リクエストが行われた後でRM送信元がダウンする

- リクエストが到着した後でRM宛先がダウンする

- バッファなしの信頼性のあるWebサービスでの障害シナリオ

- 信頼性のあるWebサービスの作成および呼出し手順

- 送信元と宛先のWebLogic Serverインスタンスの構成

- Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成

- WS-ReliableMessagingポリシー・アサーション・バージョン1.2と1.1を使用したカスタムWS-Policyファイルの作成

- WS-ReliableMessagingポリシー・アサーション・バージョン1.0を使用したカスタムWS-Policyファイルの作成(非推奨)

- 複数のポリシー選択肢の使用

- 信頼性のあるJWSファイルに関するプログラミングのガイドライン

- Webサービス・クライアントからの信頼性のあるWebサービスの呼出し

- 信頼性のあるメッセージングの構成

- WebLogic Serverでの信頼性のあるメッセージングの構成

- 管理コンソールの使用

- WLSTの使用

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

- Webサービス・クライアントでの信頼性のあるメッセージングの構成

- 基本の再送信間隔の構成

- WebLogic ServerまたはWebサービス・エンドポイントでの基本の再送信間隔の構成

- Webサービス・クライアントでの基本の再送信間隔の構成

- 再送信間隔の指数関数的バックオフの構成

- WebLogic ServerまたはWebサービス・エンドポイントでの再送信間隔の指数関数的バックオフの構成

- Webサービス・クライアントでの再送信間隔の指数関数的バックオフの構成

- 順序の有効期限の構成

- WebLogic ServerまたはWebサービス・エンドポイントでの順序の有効期限の構成

- Webサービス・クライアントでの順序の有効期限の構成

- 非アクティブ・タイムアウトの構成

- WebLogic ServerまたはWebサービス・エンドポイントでの非アクティブ・タイムアウトの構成

- Webサービス・クライアントでの非アクティブ・タイムアウトの構成

- Webサービスのバッファなし宛先の構成

- 確認応答の間隔の構成

- 信頼性エラー・リスナーの実装

- 信頼性のあるメッセージ・シーケンスのライフサイクルの管理

- 信頼性のあるシーケンスの管理

- 信頼性のあるシーケンスIDの取得および設定

- 信頼性のあるシーケンスの状態へのアクセス

- クライアントIDの管理

- 確認応答済みリクエストの管理

- メッセージに関する情報へのアクセス

- 信頼性のあるシーケンスでの最後のメッセージの識別

- 信頼性のあるシーケンスを閉じる

- 信頼性のあるシーケンスの終了

- 新しいメッセージ・シーケンスを開始するためのクライアントのリセット

- Webサービスの信頼性のあるメッセージングの監視

- ビジネス作業単位へのメッセージのグループ化(バッチ化)

- 信頼性のあるWebサービスを再デプロイする際にクライアント側で考慮すべき事項

- WebLogic Web サービスの信頼性のあるメッセージングとの相互運用性

15 Webサービス原子性トランザクションの使用

- Webサービス原子性トランザクションの概要

- Webサービスの高度な機能に必要なドメイン・リソースの構成

- Webサービスに対するWebサービス原子性トランザクションの有効化

- JWSファイルでの@Transactionalアノテーションの使用

- 例: Webサービス・クラスでの@Transactionalアノテーションの使用

- 例: Webサービス・メソッドでの@Transactionalアノテーションの使用

- 例: @TransactionalアノテーションとEJB @TransactionAttributeアノテーションの併用

- WSDLから開始するWebサービス原子性トランザクションの有効化

- Webサービス・クライアントに対するWebサービス原子性トランザクションの有効化

- @Transactionalアノテーションと@WebServiceRefアノテーションの併用

- TransactionalFeatureをクライアントに渡す

- 管理コンソールを使用したWebサービス原子性トランザクションの構成

- コーディネータと参加者の間で交換されるメッセージの保護

- Webサービス原子性トランザクションの有効化および構成

- クラスタ環境でのWebサービス原子性トランザクションの使用

- Webサービス原子性トランザクションのその他の使用例

16 Fast Infosetを使用したXML転送の最適化

- Fast Infosetの概要

- WebサービスでのFast Infosetの有効化

- Webサービス・クライアントでのFast Infosetの有効化および構成

- コンテンツ・ネゴシエーション戦略の構成

- 設計時にFastInfosetClientFeature機能クラスを使用する例

- WebサービスおよびクライアントでのFast Infosetの無効化

17 SOAP Over JMSトランスポートの使用

- SOAP Over JMSトランスポートの概要

- JMSトランスポート用のWebLogic Serverドメインの構成

- JMSトランスポートを使用したWebサービスの開発: Javaからの開始

- @JMSTransportServiceアノテーションの使用

- Ant build.xmlファイルでの<jmstransportservice>子要素の使用

- JMSトランスポートを使用したWebサービスの開発: WSDLからの開始

- JMSトランスポートを使用するためのWSDLの更新

- WSDLバインディング・レベルでのJMSトランスポートの有効化

- WSDLでのJMSトランスポート・プロパティの構成

- WSDLでのJMSトランスポートの有効化の例

- JMSトランスポートを使用したWebLogic Webサービスの呼出し

- Ant build.xmlファイルでの<jmstransportclient>要素の使用

- @JMSTransportClientアノテーションの使用

- JMSTransportClientFeatureクライアントAPIの使用

- ターゲット・エンドポイント・アドレスとしてのJMS URIの構成

- AsyncClientTransportFeatureを使用した非同期クライアントの構成

- JMSトランスポート・プロパティの構成

- JMSトランスポート構成プロパティの説明

- 構成メソッドと優先順位

- 管理コンソールを使用したJMSトランスポートの構成

- WLSTを使用したJMSトランスポートの構成

- JMS URIの構成

- JMSリクエストURIの構成

- WS-Addressingヘッダーの構成

- JMSレスポンス・キューの構成

- JMSメッセージ・タイプの構成

- WSDLファイルへのHTTPアクセスの構成

- SOAP Over JMSトランスポートの監視

18 SOAPメッセージ・ハンドラの作成と使用

- SOAPメッセージ・ハンドラの概要

- サーバー側SOAPメッセージ・ハンドラの追加:主な手順

- クライアント側SOAPメッセージ・ハンドラの追加:主な手順

- SOAPメッセージ・ハンドラおよびハンドラ・チェーンの設計

- サーバー側ハンドラの実行

- クライアント側ハンドラの実行

- SOAPメッセージ・ハンドラの作成

- SOAPハンドラのサンプル

- 論理ハンドラのサンプル

- Handler.handleMessage()メソッドの実装

- Handler.handleFault()メソッドの実装

- Handler.close()メソッドの実装

- メッセージ・コンテキスト・プロパティの値とメソッドの使用

- SAAJを使用したSOAPリクエスト・メッセージおよびレスポンス・メッセージの直接操作

- SOAPPartオブジェクト

- AttachmentPartオブジェクト

- SOAPメッセージ・ハンドラで画像添付ファイルの操作

- JWSファイルでのハンドラ・チェーンの構成

- ハンドラ・チェーン構成ファイルの作成

- Webサービスのコンパイルと再ビルド

- クライアント側SOAPメッセージ・ハンドラの構成

19 SOAPフォルトを使用した例外処理

- SOAPフォルトを使用した例外処理の概要

- SOAPフォルト要素のコンテンツ

- SOAP 1.2 <Fault>要素のコンテンツ

- SOAP 1.1 <Fault>要素のコンテンツ

- モデル化されたフォルトの使用

- カスタム例外の作成と使用

- モデル化されたフォルトのWSDLファイルにおけるマッピングの仕組み

- SOAPメッセージによるフォルト通知の仕組み

- Webサービス・クライアントの作成

- 生成されたJava例外クラスの確認

- 生成されたJavaフォルトBeanクラスの確認

- クライアント側のサービス実装の確認

- クライアント実装クラスの作成

- モデル化されていないフォルトの使用

- 例外処理プロセスのカスタマイズ

- SOAPフォルトからのスタック・トレースの無効化

- その他の例外

20 バイナリ・データ転送の最適化

- MTOM/XOPを使用したバイナリ・データ転送の最適化

- データ型のアノテーションの追加

- データ型のアノテーションを追加する: Javaから始める場合

- データ型のアノテーションを追加する: WSDLから始める場合

- WebサービスでMTOMの有効化

- アノテーションを使用してWebサービスでMTOMの有効化

- WS-PolicyファイルをアタッチしてWebサービスでMTOMの有効化

- クライアントでMTOMの有効化

- 添付ファイルのしきい値の設定

- HTTPチャンクの有効化

- SOAP添付ファイルのストリーミング

- クライアント側のサンプル

- サーバー側のサンプル

- SOAP添付ファイルのストリーミングの構成

- サーバーでSOAP添付ファイルのストリーミングの構成

- クライアントでSOAP添付ファイルのストリーミングの構成

- swaRefを使用した添付ファイル付きSOAPメッセージの送信

21 Webサービス永続性の管理

- Webサービス永続性の概要

- Webサービス永続性を構成するためのロードマップ

- Webサービス永続性の構成

- 論理ストアの構成

- Webサービス・エンドポイントのWebサービス永続性の構成

- Webサービス・クライアントのWebサービス永続性の構成

- クラスタでのWebサービス永続性の使用

- Webサービス永続性のクリーンアップ

22 Webサービスのメッセージ・バッファリングの構成

- メッセージ・バッファリングの概要

- メッセージ・バッファリングの構成

- リクエスト・キューの構成

- レスポンス・キューの構成

- メッセージの再試行回数と遅延の構成

23 クラスタ内のWebサービスの管理

- Webサービス・クラスタでのルーティングの概要

- クラスタでのルーティングのシナリオ

- シナリオ1: 単一サーバーへのWebサービス・レスポンスのルーティング

- シナリオ2: ルーティング情報を使用した単一サーバーへのWebサービス・レスポンスのルーティング

- シナリオ3: IDを使用した単一サーバーへのWebサービス・レスポンスのルーティング

- Webサービス・クラスタでのルーティングの仕組み

- 送信するリクエストへのルーティング情報の追加

- 受信したリクエストのルーティング情報の検出

- クラスタ内でのリクエストのルーティング

- フロントエンドSOAPルーターでのルーティング・マップの保持

- X-weblogic-wsee-storetoserver-list HTTPレスポンス・ヘッダー

- X-weblogic-wsee-storetoserver-hash HTTPレスポンス・ヘッダー

- クラスタ内のWebサービスの構成

- WebLogicクラスタの設定

- クラスタ環境におけるWebサービスの高度な機能に必要なドメイン・リソースの構成

- フロントエンドSOAPルーターの拡張によるWebサービスのサポート

- Webサービス原子性トランザクション・メッセージのルーティングの有効化

- Webサービスの接続作成メッセージのルーティングの有効化

- フロントエンドSOAPルーターのIDの構成

- ネットワーク・チャネルを使用したフロントエンドSOAPルーターのIDの構成

- クラスタのルーティング・パフォーマンスのモニター

24 プロバイダベース・エンドポイントおよびディスパッチ・クライアントを使用したSOAPメッセージの操作

- Webサービス・プロバイダベース・エンドポイントおよびディスパッチ・クライアントの概要

- XMLレベルでの処理のための使用モードとメッセージ・フォーマット

- Webサービス・プロバイダベース・エンドポイントの開発(Javaから始める場合)

- 同期プロバイダベース・エンドポイントの開発

- 非同期プロバイダベース・エンドポイントの開発

- メッセージ・フォーマットの指定

- JWSファイルによるWebサービス・プロバイダの実装の指定(@WebServiceProviderアノテーション)

- 使用モードの指定(@ServiceModeアノテーション)

- 同期プロバイダベース・エンドポイントのinvoke()メソッドの定義

- 非同期プロバイダベース・エンドポイントのinvoke()メソッドの定義

- 非同期プロバイダベース・エンドポイントのコールバック・ハンドラの定義

- Webサービス・プロバイダベース・エンドポイントの開発(WSDLから始める場合)

- プロバイダベース・エンドポイントでのSOAPハンドラの使用

- Webサービス・ディスパッチ・クライアントの開発

- Webサービス・ディスパッチ・クライアントの例

- ディスパッチ・インスタンスの作成

- Webサービス操作の呼出し

25 SOAPヘッダーの送受信

- SOAPヘッダーの送受信の概要

- WSBindingProviderを使用したSOAPヘッダーの送信

- WSBindingProviderを使用したSOAPヘッダーの受信

26 コールバックの使用

- コールバックの概要

- コールバック実装のサンプル

- コールバックのプログラミング手順

- ターゲットWebサービスのプログラミングのガイドライン

- コールバック・クライアントWebサービスのプログラミングのガイドライン

- コールバックWebサービスのプログラミングのガイドライン

- ターゲットWebサービスのbuild.xmlファイルの更新

27 動的プロキシ・クライアントの開発

- 静的プロキシ・クライアントと動的プロキシ・クライアントの概要

- 動的プロキシ・クライアントの開発手順

- WSDLの場所を指定する際のその他の考慮事項

28 Webサービスのエンドポイントのパブリッシュ

29 XMLカタログの使用

- XMLカタログの概要

- XMLカタログの定義と参照

- 外部XMLカタログの定義

- 外部XMLカタログ・ファイルの作成

- 外部XMLカタログ・ファイルの参照

- XMLカタログを埋め込み

- 埋め込みXMLカタログの作成

- 埋め込みXMLカタログの参照

- クライアント・ランタイムでのXMLカタログの無効化

- XMLリソースのローカル・コピーの取得

30 XML over HTTPを使用するWebサービスのプログラミング

- XML over HTTPを使用するWebサービスのプログラミングの概要

- XML over HTTPを使用するWebサービスのプログラミングのガイドライン

- クライアントからWebサービスにアクセスする

- XML over HTTPを使用するWebサービスの保護

31 HTTPセッションを使用したステートフルJAX-WS Webサービスのプログラミング

- ステートフルWebサービスの概要

- サーバーでHTTPセッションにアクセスする

- クライアントでのHTTPセッションの有効化

- セッション状態レプリケーションを使用してクラスタ内のステートフル・サービスを開発する

- JAX-WS RI @ステートフル拡張に関する注意

32 Webサービスのテストおよび監視

- Webサービスのテスト

- Webサービスおよびクライアントの監視

- Webサービスの監視

- Webサービス・クライアントの監視

- ワーク・マネージャによるWebサービス作業の優先付けとスタック実行スレッドの削減

第V部 リファレンス

A Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル

- DefaultReliability1.2.xml (WS-Policyファイル)

- DefaultReliability1.1.xml (WS-Policyファイル)

- DefaultReliability.xml WS-Policyファイル(WS-Policy)[非推奨]

- LongRunningReliability.xml WS-Policyファイル(WS-Policy)[非推奨]

- Mc1.1.xml (WS-Policyファイル)

- Mc.xml (WS-Policyファイル)

- Reliability1.2_ExactlyOnce_WithMC1.1.xml (WS-Policyファイル)

- Reliability1.2_SequenceSTR.xml (WS-Policyファイル)

- Reliability1.1_SequenceSTR.xml (WS-Policyファイル)

- Reliability1.2_SequenceTransportSecurity.xml (WS-Policyファイル)

- Reliability1.1_SequenceTransportSecurity.xml (WS-Policyファイル)

- Reliability1.0_1.2.xml (WS-Policyファイル)

- Reliability1.0_1.1.xml (WS-Policy.xmlファイル)

B 信頼性のあるメッセージングのバッチ化のためのクライアント・ラッパー・クラスの例

C JAX-WSへのJAX-RPC Webサービスおよびクライアントの移行

- WebLogic Webサービスの最終コンテキスト・ルートの設定

- WebLogic独自のアノテーションの使用

- WSDLファイルの生成

- JAXBカスタム・タイプの使用

- EJB 3.0の使用

- RPCスタイルSOAPバインディングからの移行

- SOAPメッセージ・ハンドラの更新

- JAX-WSクライアントの呼出し

はじめに

ここでは、『Oracle WebLogic Server 12.1.3 JAX-WS Webサービスの開発』で使用されるドキュメントのアクセシビリティ機能と表記規則について説明します。

ドキュメントのアクセシビリティについて

Oracleのアクセシビリティについての詳細情報は、Oracle Accessibility ProgramのWebサイトhttp://www.oracle.com/pls/topic/lookup?ctx=acc&id=docaccを参照してください。

Oracleサポートへのアクセス

サポートをご購入のOracleのお客様は、My Oracle Supportにアクセスして電子サポートを受けることができます。詳細情報はhttp://www.oracle.com/pls/topic/lookup?ctx=acc&id=infoか、聴覚に障害があるお客様はhttp://www.oracle.com/pls/topic/lookup?ctx=acc&id=trsを参照してください。

表記規則

このドキュメントでは次の表記規則を使用します。

規則

意味

太字

太字は、操作に関連するGraphical User Interface要素、または本文中で定義されている用語および用語集に記載されている用語を示します。

斜体

イタリックは、ユーザーが特定の値を指定するプレースホルダー変数を示します。

固定幅フォント

固定幅フォントは、段落内のコマンド、URL、サンプル内のコード、画面に表示されるテキスト、または入力するテキストを示します。

このガイドでの新しい情報

次のトピックでは、Oracle Fusion Middleware 12c (12.1.3)でのWebLogic Java API for XML Web Services (JAX-WS) Webサービスの新機能と変更された機能を説明し、追加情報の参照先を示しています。

12c (12.1.3)での新機能と変更された機能

Oracle Fusion Middleware 12c (12.1.3)について、この機能ドキュメントに記載されている新機能および変更された機能はありません。

12c (12.1.2)での新機能と変更された機能

このドキュメントにおける、Oracle Fusion Middleware 12c (12.1.2)の新機能と変更された機能は次のとおりです。

- Fast Infoset。圧縮されたバイナリ・エンコーディング・フォーマットで、テキストベースのXMLフォーマットより効率的にシリアライズできます。Fast Infosetでは、ドキュメント・サイズと処理パフォーマンスの両方が最適化されます。第16章「Fast Infosetを使用したXML送信の最適化」を参照してください。

- 接続プロトコル・オプションとしてのSOAP over Java Messaging Service (JMS)トランスポート。これによりWebサービスおよびクライアントは、HTTP接続ではなくJMS宛先を使用して通信できるようになります。第17章「SOAP Over JMSトランスポートの使用」を参照してください。

- 新しいスタンドアロンWebサービス・クライアントJARファイル。基本的なJAX-WSクライアント側機能およびOracle Web Services Manager (OWSM)セキュリティ・ポリシー・サポートがサポートされます。「スタンドアロンのJava SEクライアントからのWebサービスの呼出し」を参照してください。

- Webサービスの高度な機能をテストするため、拡張されたWebサービス・テスト・クライアント。「Webサービスのテスト」を参照してください。

- Oracle Fusion Middlewareリリース11gで提供されていた次のガイドの内容が、1つのドキュメントにまとめられています。

- Oracle WebLogic Server JAX-WS Webサービス・スタート・ガイド

- Oracle WebLogic Server JAX-WS Webサービスの高度な機能のプログラミング

第I部

概要

第I部では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic (Java EE) Webサービスの開発について説明します。

ここで説明する内容は次のとおりです。

- 第1章「JAX-WS Webサービスの概要」

- 第2章「JAX-WS Webサービス開発者向けの例」

1 JAX-WS Webサービスの概要

この章では、Java API for XML-based Web services (JAX-WS)を使用するWebLogic Server 12.1.3用のWebLogic (Java EE) Webサービスの開発方法の概要を説明します。JAX-WSは、Java Webサービスのコーディング、構築、デプロイメントに使用する標準ベースのAPIです。

この章の内容は次のとおりです:

- JAX-WS Webサービス開発の概要

- JAX-WS Webサービスを実装するためのロードマップ

このマニュアルやその他のマニュアルの用語の定義については、「用語集」を参照してください。

JAX-WS Webサービス開発の概要

WebLogic WebサービスはJSR 109: Implementing Enterprise Web Services仕様(http://www.jcp.org/en/jsr/detail?id=109)に従って実装されています。この仕様では、JavaでWebサービスを実装するための標準のJava EE実行時アーキテクチャを定義しています。また、標準Java EE Webサービスのパッケージ化形式、デプロイメント・モデル、実行時サービスについても記述されており、そのすべてをWebLogic Webサービスで実装しています。

以降の項で説明する内容は、次のとおりです。

- プログラミング・モデル - メタデータ・アノテーション

- 開発モデル - ボトムアップとトップダウン

プログラミング・モデル - メタデータ・アノテーション

JSR 109: Implementing Enterprise Web Services仕様(http://www.jcp.org/en/jsr/detail?id=109)では、Java EE Webサービスは次のいずれかのコンポーネントによって実装するものと定められています。

- Webコンテナ内で動作するJavaクラス

- EJBコンテナ内で動作するステートレスまたはシングルトン・セッションEJB

JavaクラスまたはEJBのコードは、Webサービスのビジネス・ロジックを実装します。生のJavaクラスまたはEJBを直接コーディングするかわりに、JWSアノテーション・プログラミング・モデルを使用することをお薦めします。それによって、WebLogic Webサービスのプログラミングがより簡単になります。

このプログラミング・モデルでは、JDKメタデータ・アノテーション機能を利用しています。アノテーション付きのJavaファイルを作成し、Antタスクを使用してそのファイルをJavaクラスにコンパイルし、関連するアーティファクトをすべて生成します。アノテーション付きのJava Webサービス(JWS)ファイルは、Webサービスの中核部分です。このファイルにはWebサービスの動作を決定するJavaコードが含まれています。JWSファイルは、アノテーションを使用してWebサービスの形式や特性を指定した、通常のJavaクラス・ファイルです。JWSファイルで使用できるJWSアノテーションには、Web Services Metadata for the Java Platform仕様(http://www.jcp.org/en/jsr/detail?id=181)で定義された標準のアノテーションと、その他の標準またはWebLogic固有のアノテーションがあり、作成するWebサービスのタイプに応じて使い分けます。

基本的なWebLogic Webサービスをコーディングしたら、追加の高度な機能をプログラミングおよび構成できます。たとえば、SOAPメッセージのデジタル署名や暗号化を指定できます(http://www.oasis-open.org/committees/tc_home.php?wg_abbrev=wssのWS-Security仕様で規定)。このようなWebLogic Webサービスの高度な機能は、WS-Policyファイルを使用して構成します。WS-PolicyファイルはWS-Policy仕様に準拠するXMLファイルです。セキュリティや信頼性のあるメッセージングの構成を記述するための、セキュリティに固有のXML要素やWebサービスの信頼性のあるメッセージングに固有のXML要素が含まれています。

開発モデル - ボトムアップとトップダウン

Webサービスの開発には、ボトムアップとトップダウンという2つのアプローチがあります。次の項でそれぞれのアプローチについて説明します。

ボトムアップ・アプローチ: Javaから開始

ボトムアップ・アプローチでは、JWSファイルを最初から開発します。JWSファイルを作成したら、jwsc WebLogic WebサービスのAntタスクを使用して、JWSファイルをコンパイルします。http://www.jcp.org/en/jsr/detail?id=109で「JSR 109: Implementing Enterprise Web Services」仕様を参照してください。

jwsc Antタスクでは、JWSファイルは常にプレーンJavaクラスにコンパイルされます。ステートレスまたはシングルトン・セッションEJBが実装されるのは、JWSファイルにステートレスまたはシングルトン・セッションEJBを実装している場合のみです。jwsc Antタスクは、Webサービスの補助的なアーティファクトもすべて生成し、アーカイブ・ファイルにすべてをパッケージ化して、WebLogic Serverにデプロイできるエンタープライズ・アプリケーションを作成します。

jwsc Antタスクのデフォルトでは、Webサービスはすべての標準WARアーティファクトとともに標準のWebアプリケーションWARファイルにパッケージ化されます。ただし、このWARファイルには、それがWebサービスでもあることを示す追加のアーティファクトが含まれています。追加のアーティファクトには、デプロイメント記述子ファイル、Webサービスのパブリック規約を記述したWSDLファイルなどがあります。jwscを複数のJWSファイルに対して実行する場合は、jwscが複数のWebサービスを1つのWARファイルにパッケージ化するか、Webサービスごとに別々のWARファイルにパッケージ化するかを選択できます。どちらを選択した場合でも、jwscによって1つのエンタープライズ・アプリケーションが生成されます。

JWSファイルにステートレスまたはシングルトン・セッションEJBを実装した場合、jwsc Antタスクは、ejb-jar.xmlおよびweblogic-ejb.jar.xmlデプロイメント記述子ファイルなどの通常のアーティファクトをすべて含めて、Webサービスを標準のEJB JARにパッケージ化します。EJB JARファイルには、前述のような、Webサービスであることを示すWebサービスに固有の追加のアーティファクトも含まれています。同様に、複数のJWSファイルを1つのEJB JARファイルにパッケージ化するか、複数のEJB JARファイルにパッケージ化するかを選択できます。

または、build.xmlファイルのjwsc Antタスクを更新して、module子要素のejbWsInWar属性を有効にすることにより、セッションEJBがWebアプリケーションのWARファイルとしてパッケージ化されるように指定できます。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』の「jwsc」を参照してください。

ボトムアップ・アプローチの詳細は、「Javaから開始するWebLogic Webサービスの開発: 主な手順」を参照してください。

トップダウン・アプローチ: WSDLから開始

トップダウン・アプローチでは、WSDLファイルからWebサービスを作成します。wsdlc Antタスクを使用して、WSDLファイルで記述されたWebサービスの部分的な実装を生成することができます。JWSサービス・エンドポイント・インタフェース(SEI)、途中まで作成済みのJWSクラス・ファイル、XMLスキーマ・データ型を表すJavaBeanなどが、wsdlc Antタスクによって出力ディレクトリ内に生成されます。

wsdlc Antタスクを実行(通常は1回のみ)したら、メソッドをビジネス要件どおりに実行するためにそのメソッドにJavaコードを追加するなどして、生成されたJWS実装ファイルを更新します。wsdlc Antタスクは、WSDLファイルを基にWebサービスの形式を認識していますが、そのWebサービスをどのように実行するかについては認識していないので、最初は生成されたJWS実装ファイルにビジネス・ロジックは含まれていません。

wsdlc AntタスクはJWS SEIとデータ・バインディング・アーティファクトを一緒にJARファイルにパッケージ化します。このJARファイルを後でjwsc Antタスクに指定します。このJARファイルを更新する必要はありません。更新するファイルはJWS実装クラスのみです。

トップダウン・アプローチの詳細は、「WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順」を参照してください。

JAX-WS Webサービスを実装するためのロードマップ

次の表に、WebLogic Serverを使用したJAX-WS Webサービスおよびクライアントの開発、パッケージ化とデプロイ、呼出しおよび管理における一般的なタスクのロードマップを示します。

表1-1 JAX-WS Webサービスを実装するためのロードマップ

章

内容

第I部「基本的なJAX-WS Webサービスの開発」

WebLogic開発環境で基本的なJAX-WS Webサービスを開発します。Webサービスを実装するJWSファイルをプログラミングし、Java Architecture for XML Binding (JAXB)データ・バインディングを使用します。

第I部「基本的なJAX-WS Webサービス・クライアントの開発」

JAX-WSを使用してWebLogic Webサービス・クライアントを開発し、ベスト・プラクティスを適用します。

第I部「JAX-WS Webサービスの高度な機能の開発」

JAX-WSを使用してWebLogic Webサービスの高度な機能を開発します。高度な機能には、非同期クライアント、信頼性のあるメッセージング、原子性トランザクションなどが含まれます。Webサービスのテストおよび監視を行います。

第I部 リファレンス

Webサービスの信頼性のあるメッセージングおよび接続作成に対するあらかじめパッケージ化されたWS-Policyファイルの使用、信頼性のあるバッチ・メッセージングの使用、およびJAX-RPC WebサービスおよびクライアントのJAX-WSへの移行を行います。

注意:
Oracle WebLogic ServerのJAX-WS実装は、JAX-WS参照実装(RI)から拡張されて、Glassfish Communityによって開発されます(http://jax-ws.java.net/を参照してください)。JAX-WS仕様(JSR-224)で定義されたすべての機能は、Oracle WebLogic Serverによって完全にサポートされます。
また、JAX-WS RIにはGlassfishコントリビュータによって提供された様々な拡張があります。特に記載しないかぎり、JAX-WS RI拡張はOracle WebLogic Serverでの使用についてはサポートされません。

WebLogic Webサービスの概要、規格、サンプルおよび関連ドキュメントは、『Oracle WebLogic Server WebLogic Webサービスの理解』を参照してください。WebLogic Webサービスのセキュリティについては、『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』および『Oracle WebLogic Server WebLogic Webサービスの保護』を参照してください。

2 JAX-WS Webサービス開発者向けの例

この章では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの開発例を示します。

表2-1 JAX-WS Webサービス開発者向けの例

例

詳細情報

Webサービス・サンプル・アプリケーション

『Oracle WebLogic Server WebLogic Webサービスの理解』のJava EE Webサービス開発者向けの例に関する項

一般的なWebサービス・コード例

第6章「JAX-WS Webサービスの開発例」

一般的なWebサービス・クライアント例

第9章「JAX-WS Webサービス・クライアントの開発例」

高度なWebサービス・クライアント例

例7-1「Webサービス・クライアントのベスト・プラクティスの例」

非同期Webサービス・クライアント例

例11-1「非同期Webサービス・クライアントのベスト・プラクティスの例」

信頼性のあるWebサービス・クライアント例

例13-1「信頼性のあるWebサービス・クライアントのベスト・プラクティスの例」

第II部

基本的なJAX-WS Webサービスの開発

第II部では、Java API for XML-based Web Services (JAX-WS)を使用して基本的なWebLogic Webサービスを開発する方法について説明します。

ここで説明する内容は次のとおりです。

- 第3章「JAX-WS Webサービスの開発」

- 第4章「JWSファイルのプログラミング」

- 第5章「JAXBデータ・バインディングの使用」

- 第6章「JAX-WS Webサービスの開発例」

3 JAX-WS Webサービスの開発

この章では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの反復的な開発プロセスについて説明します。

この章では、以下のトピックについて説明します。

- WebLogic Webサービス・プログラミング・モデルの概要

- 高度なWebサービス機能のためのドメインの構成

- Javaから開始するWebLogic Webサービスの開発: 主な手順

- WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順

- 基本的なAnt build.xmlファイルの作成

- jwsc WebLogic WebサービスAntタスクの実行

- wsdlc WebLogic WebサービスAntタスクの実行

- wsdlcで生成される途中まで作成済みのJWS実装クラス・ファイルの更新

- WebLogic Webサービスのデプロイとアンデプロイ

- WebサービスのWSDLの参照

- 動的なWSDLで指定されたサーバー・アドレスの構成

- Webサービスのテスト

- WebサービスのWebLogic分割開発ディレクトリ環境への統合

WebLogic Webサービス・プログラミング・モデルの概要

WebLogic Webサービスのプログラミング・モデルはJWSファイル(JWSアノテーションを使用してWebサービスの形式や動作を指定したJavaファイル)と、JWSファイルを実行するAntタスクを中心に展開されます。JWSアノテーションはJDKバージョン5.0で導入されたメタデータ機能に基づいており(JSR-175 http://www.jcp.org/en/jsr/detail?id=175で規定)、Web Services Metadata for the Java Platform仕様(JSR-181)(http://www.jcp.org/en/jsr/detail?id=181)およびJAX-WS仕様(JSR-224)(http://jax-ws.java.net)で定義された標準のアノテーションと追加のアノテーションがあります。サポートされているJWSアノテーションの完全なリストについては、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』の「Webサービスのアノテーション・サポート」を参照してください。このプログラミング・モデルに関するその他の詳細情報は、「プログラミング・モデル - メタデータ・アノテーション」を参照してください。

Webサービスは、2つの開発手法(ボトムアップまたはトップダウン)を使用して作成できます。ボトムアップ開発は、SOAPを使用して基礎となるJava実装からWebサービスを開発するプロセスを意味します。トップダウン開発は、WSDLソースからWebサービスを開発することを意味します。

次の項では、Webサービスを繰返し開発する主要な手順を、Javaから開始する場合(ボトムアップ)、または既存のWSDLファイルから開始する場合(トップダウン)について説明します。

- Javaから開始するWebLogic Webサービスの開発: 主な手順

- WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順

反復的な開発とは、希望どおりに動作するまで、Webサービスを繰返しコーディング、コンパイル、パッケージ化、デプロイ、およびテストできるように、開発環境を設定することです。WebLogic Webサービス・プログラミング・モデルでは、Antタスクを使用して、反復的な開発のほとんどの手順を実行します。一般に、すべての手順に対応するターゲットを含んだ1つのbuild.xmlファイルを作成して、そのターゲットを繰返し実行します。JWSファイルを新しいJavaコードで更新したら、その更新が期待どおりに動作することをテストします。

この項で説明されているコマンドライン・ツールの他に、Webサービスを開発するためにOracle JDeveloperまたはOracle Enterprise Pack for Eclipse (OEPE)のようなIDEを使用できます。詳細は、『Oracle WebLogic Server WebLogic Webサービスの理解』のOracle IDEを使用したWebサービスの構築に関する項を参照してください。

高度なWebサービス機能のためのドメインの構成

ドメインを作成または拡張する際には、JAX-WS拡張用のWebLogicの高度なWebサービス・テンプレート(wls_webservice_jaxws.jar)を適用して、次に示す高度なWebサービス機能のサポートに必要なリソースを自動的に構成できます。

- 非同期メッセージング(第12章「非同期クライアントの開発」を参照)。

- Webサービスの信頼性のあるメッセージング(第14章「Webサービスの信頼性のあるメッセージングの使用」を参照)。

- メッセージ・バッファリング(第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照)。

- WS-SecureConversationを使用したセキュリティ(『Oracle WebLogic Server WebLogic Webサービスの保護』のメッセージレベルのセキュリティの構成に関する項を参照)。

注意:
SOAP over JMSトランスポートのドメインを構成するには、「JMSトランスポート用のWebLogic Serverドメインの構成」を参照してください。

WebLogic Advanced Web Services for JAX-WS拡張テンプレートは、高度なWebサービスのリカバリ可能性を保証する必要がある場合にのみ、使用する必要があります。拡張テンプレートでは、WebLogic Serverがサーバーの障害時に重要な状態の情報を保持できるようにすることでリカバリ可能性をサポートする、次のリソースを構成します。

- 信頼性のあるメッセージング・リクエストを格納するJMSキュー。

- Webサービス用のパフォーマンスの高い組込みストレージ・ソリューションを提供するデフォルトのWebサービス永続性の構成。

WebLogic Advanced Web Services for JAX-WS拡張テンプレートを使用するときの利点は次のとおりです。

- Webサービスおよびクライアントは、信頼性があり高パフォーマンスなWebLogicストレージ・ソリューションをデフォルトで使用します。

- 信頼性のあるメッセージングを使用するWebサービスは、フォルト・トレランスを向上して負荷をより適切に緩和するために、受信した非同期リクエストをバッファリングできます。(デフォルトでこの機能は有効に設定されている。)

- Webサービスとクライアント間のメッセージは、クライアント・エラーまたはサービス・エラー、あるいはその両方の発生時にフォルト・トレランスおよびリカバリ可能であるように構成できます。

WebLogic Advanced Web Services for JAX-WS拡張テンプレートを使用しない場合でも、拡張機能を使用して開発できますが、次に示すようにサービス品質は低下します。

- デフォルトでは、高度なWebサービスの状態はメモリーに格納され、サーバーの障害時にはそのデータが失われます。

- Webサービスは、信頼性のあるメッセージングの使用時に、受信した非同期リクエストをバッファリングしません。

- Webサービスとクライアントは障害の発生時にリカバリ可能ではありません。Webサービスとクライアント間を送信中のリクエストは消失します。

詳細は、「高度なWebサービス機能に必要なリソース」を参照してください。

注意:
リカバリ可能性をサポートするためにWebLogic Advanced Web Services for JAX-WS拡張テンプレートを適用しない場合は、次のようになります。

- 宛先サーバーでWebサービスの信頼性のあるメッセージングに対してバッファリングが無効となるようにする必要があります。詳細は、「Webサービスのバッファなし宛先の構成」を参照してください。

- Webサービスについて構成したサービス機能の品質が有効にならない場合があります。この場合、機能が無効になっていることを示すメッセージがサーバー・ログに記録されます。

この拡張テンプレートの使用は必須ではありませんが、使用すると必要なリソースの構成が格段に容易になります。また、これらの拡張機能に必要なリソースを、Oracle WebLogic Server管理コンソールやWLSTを使用して手動で構成することも可能です。

次の手順では、高度なWebサービス機能用にドメインを自動的に構成する方法を説明します。構成ウィザードを使用してWebLogic Serverドメインを作成および更新する詳細な手順については、構成ウィザードによるWebLogicドメインの作成を参照してください。

- 高度なWebサービス機能に必要なリソース

- 高度なWebサービス機能用にドメインを拡張するスクリプト

- 高度なWebサービス機能のための構成ウィザードを使用したドメインの構成

- Webサービス拡張テンプレートを使用したドメイン拡張でのWLSTの利用

- ドメインの拡張後に追加されたリソースの更新

- WebLogic Advanced Web Services for JAX-WS拡張テンプレートを適用するときの問題に関するトラブルシューティング

高度なWebサービス機能に必要なリソース

表3-1に、JAX-WS拡張用のWebLogicの高度なWebサービス・テンプレートを使用する際に自動的に定義されるリソースをリストします。

拡張テンプレートを適用しない場合は、Oracle WebLogic Server管理コンソールまたはWLSTを使用して、リソースを手動で構成する必要があります。JMSターゲット指定は、必ず『Oracle WebLogic Server JMSリソースの管理』のJMS初級ユーザーおよび上級ユーザーのベスト・プラクティスに関する項で定義されているベスト・プラクティスに従って構成してください。具体的には、次のとおりです。

- 各WebLogic Serverに、JMSサーバー、ストア・アンド・フォワード(SAF)サービス・エージェントおよび永続ストアを構成します。クラスタで、それぞれをローカルの移行可能なターゲット(サーバー以外)にターゲット指定します。ほとんどの場合、そのホスト・サーバーのデフォルトの移行可能ターゲットを指定すれば十分です。

- JMSモジュールをクラスタ(クラスタ環境を使用していない場合は単一サーバー)のターゲットに指定します。

- モジュールにつき厳密に1つのサブデプロイメントを作成し、そのサブデプロイメントを適用可能なJMSサーバーまたはSAFエージェントにのみ(サーバーはではない)に移入します。

- サブデプロイメントに対してJMS宛先をターゲット指定します(WebLogic Server管理コンソールでは高度なターゲット指定とも呼ばれます)。JMS宛先にはデフォルトのターゲット指定オプションは決して使用しないでください。

表では次の変数が使用されます。

- server_designator - 構成フレームワークにより自動的に生成されるIDを指定します。通常、このIDはauto_numberという形式です。

- uniqueID - 構成フレームワークにより自動的に生成される一意の数値IDを指定します。通常、このIDは1234などの数値です。

- server_name - ユーザー指定のサーバー名を指定します。

注意:
実行時にリソース名を変更しないでください。変更すると、実行時エラーやデータ損失が発生する可能性があります。

表3-1 高度なWebサービス機能に必要なリソース

リソース名

リソース・タイプ

説明

WseeJaxwsJmsModule

JMSモジュール

高度なWebサービスに必要なJMSリソースを定義するJMSモジュールを定義します。このJMSモジュールの関連するすべてのターゲット(サーバーをターゲットとするJMSサーバー)がJAX-WS Webサービスのサポートに使用されます。このモジュールがターゲットとするすべてのサーバーには、適切なWebサービス・リソースが構成されている必要があります。

このモジュールは、ドメイン内のすべてのサーバーにターゲット設定することをお薦めします。

注意: 共通分散宛先(UDD)としてJMSモジュールを構成する必要があります。JAX-WSでWebサービスが使用するすべてのキューは共通分散宛先である必要があります。それ以外の場合は、例外がスローされます。

分散宛先を手動で構成する方法および詳細は、『Oracle WebLogic Server JMSアプリケーションの開発』の分散宛先の使用に関する項を参照してください。

WseeJaxwsFileStore_server_designator

ファイル・ストア

WebLogic Serverが使用してI/O操作を処理し、物理ストレージ(ファイル、DBMSなど)にデータを保存したり、取得したりするファイル・ストアまたは物理ストアを指定します。

server_designatorで指定されているように、WseeJaxwsJmsModuleでターゲット設定されている各管理対象サーバーに個別のファイル・ストアが構成されます。単一のサーバー・ドメインのファイル・ストアの名前はWseeJaxwsFileStoreです。

注意: ファイル・ストアは移行可能なターゲットにターゲット設定することをお薦めします。

ファイル・ストアを手動で構成する方法は、『Oracle WebLogic Serverサーバー環境の管理』のWebLogic永続ストアの使用に関する項を参照してください。

WseeJaxwsJmsServer_server_designator

JMSサーバー

JMSサーバー管理コンテナを指定します。server_designatorで指定されているように、WseeJaxwsJmsModuleのターゲットである各管理対象サーバーに個別のJMSサーバーが構成されます。JMSサーバーは、WseeFileStore_server_designatorをファイル・ストアとして使用します。

JMSサーバーを構成する際には、次のことをお薦めします。

- JMSサーバーを移行可能なターゲットにターゲット指定します。

- 各JMSサーバーで現実的な割当てを設定します。詳細は、『Oracle WebLogic Serverのパフォーマンスのチューニング』のWebLogic JMSのチューニングに関する項を参照してください。

JMSサーバーを手動で構成するには、『Oracle WebLogic Server JMSリソースの管理』のJMS構成に関する項を参照してください。

WseeJaxwsJmsServeruniqueID

JMSサブデプロイメント

クラスタのすべての管理対象サーバーに定義されているJMSサーバーをターゲットとするJMSサブデプロイメントを指定します。

JMSサブデプロイメントを手動で構成する方法は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのJMSシステム・モジュールのサブデプロイメントの構成に関する項を参照してください。

weblogic.wsee.jaxws.mdb.DispatchPolicy

ワーク・マネージャ

アプリケーションがコンテナ内で複数の作業アイテムを同時に実行できるようにします。ドメインにワーク・マネージャが生成されると、WseeJaxwsJmsModuleのターゲットであるすべてのサーバーがターゲットになります。

注意: ワーク・マネージャ・リソースの名前は変更しないでください。

ワーク・マネージャを手動で構成するには、『Oracle WebLogic Server CommonJアプリケーションの開発』のワーク・マネージャAPIの説明に関する項を参照してください。

ReliableWseeJaxwsSAFAgent_server_name

SAFサービス・エージェント

可用性の高いJMSメッセージ生成を可能にします。server_nameで指定するように、各管理対象サーバーに個別のSAFエージェントが構成されます。SAFエージェントは、ファイル・ストアとしてWseeFileStore_server_nameを使用します。

1つのサーバー・ドメインで、SAFエージェントはReliableWseeJaxwsSAFAgentという名前になります。

SAFエージェントを構成する際には、各JMSサーバーで現実的な割当を設定することをお薦めします。詳細は、『Oracle WebLogic Serverのパフォーマンスのチューニング』のWebLogic JMSのチューニングに関する項を参照してください。

SAFサービス・エージェントを構成するには、『Oracle WebLogic Serverストア・アンド・フォワード・サービスの管理』のストア・アンド・フォワード・サービスの理解に関する項を参照してください。

WseeBufferedRequestQueue_server_designator

JMSキュー

バッファされたリクエストに使用するキューを指定します。server_nameで指定するように、各管理対象サーバーに個別のキューが構成されます。

単一のサーバー・ドメインでは、キューはWseeBufferedRequestQueueという名前になります。クラスタ・ドメインでは、各JMSキューの先頭にdist_という接頭辞が付きます。

キューを手動で構成する方法は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのキューの構成に関する項を参照してください。

WseeBufferedRequestErrorQueue_server_designator

JMSキュー

最大試行回数内に処理できないバッファされたリクエストのWseeBufferedRequestQueueに使用するエラー・キューを指定します。server_nameで指定するように、各管理対象サーバーに個別のキューが構成されます。

単一のサーバー・ドメインでは、キューはWseeBufferedRequestErrorQueueという名前になります。クラスタ・ドメインでは、各JMSキューの先頭にdist_という接頭辞が付きます。

キューを手動で構成する方法は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのキューの構成に関する項を参照してください。

WseeBufferedResponseQueue_server_designator

JMSキュー

バッファされたレスポンスに使用するキューを指定します。server_designatorで指定するように、各管理対象サーバーに個別のキューが構成されます。

単一のサーバー・ドメインでは、キューはWseeBufferedResponseQueueという名前になります。クラスタ・ドメインでは、各JMSキューの先頭にdist_という接頭辞が付きます。

キューを手動で構成する方法は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのキューの構成に関する項を参照してください。

WseeBufferedResponseErrorQueue_server_designator

JMSキュー

最大再試行回数内で配信できないバッファされたレスポンス用にWseeBufferedResponseQueueに使用するエラー・キューを指定します。server_designatorで指定するように、各管理対象サーバーに個別のキューが構成されます。

単一のサーバー・ドメインでは、キューはWseeBufferedResponseErrorQueueという名前になります。クラスタ・ドメインでは、各JMSキューの先頭にdist_という接頭辞が付きます。

キューを手動で構成する方法は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのキューの構成に関する項を参照してください。

WseeStore

論理ストア

論理ストアを定義します。WseeJaxwsJmsModuleのターゲットである各管理対象サーバーに個別の論理ストアが構成されます。論理ストアは構成およびファイル・ストアにWseeBufferedRequestQueueキューを指定します。

論理ストアを手動で構成するには、「論理ストアの構成」を参照してください。

高度なWebサービス機能用にドメインを拡張するスクリプト

WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)のJARファイルには、既存のドメインを拡張してWebLogic Advanced Web Services for JAX-WS拡張テンプレートを使用する場合に役立つ次の2つのPythonスクリプトがあります。

注意:
いずれかのスクリプトを実行する前に、JMSモジュールがドメイン内のすべてのサーバーにターゲット設定されていることを確認する必要があります。

表3-2 高度なWebサービス機能用にドメインを拡張するスクリプト

スクリプト

説明

wls_webservice_complete_update_utils.py

WLSTスクリプト内から拡張テンプレートを使用してドメインを拡張できます。詳細および例については、「Web Services拡張テンプレートでドメインを拡張するためのWLSTの使用」を参照してください。

wls_webservice_complete_update.py

Javaのコマンド・ラインから拡張テンプレートを使用してドメインを拡張できます。例:

java weblogic.WLST -i wls_webservice_complete_update.py <domain-dir>

高度なWebサービス機能のための構成ウィザードを使用したドメインの構成

次の項では、高度なWebサービス機能のためにドメインを構成する方法について説明します。

- Webサービス拡張テンプレートを使用したドメインの作成

- Webサービス拡張テンプレートを使用したドメインの拡張

Webサービス拡張テンプレートを使用したドメインの作成

高度なWebサービス機能用に自動的に構成されるドメインを作成するには:

1. 構成ウィザードを起動します。

2. 「ようこそ」ウィンドウで、「新しいWebLogicドメインの作成」を選択します。

3. 「次へ」をクリックします。

4. 「次の製品をサポートするために、自動的に構成されたドメインを生成する」を選択し、JAX-WS拡張用のWebLogicの高度なWebサービスを選択します。

5. 「次へ」をクリックします。

6. ドメインの名前と場所を入力し、「次へ」をクリックします。

7. 管理者ユーザーの名前とパスワードを構成し、「次へ」をクリックします。

8. サーバーの起動モードとJDKを構成し、「次へ」をクリックします。

9. 追加のサーバーおよびクラスタを構成するには:

1. 管理対象サーバーおよびクラスタを定義するには、「オプションの構成を選択」画面で、少なくとも「管理対象サーバー、クラスタ、およびマシン」を選択します。必要に応じて、その他のアイテムを選択し「次へ」をクリックします。

2. 環境の管理対象サーバーを構成し、「次へ」をクリックします。

3. 環境のクラスタを構成し、「次へ」をクリックします。

4. 「クラスタに割当て」画面でクラスタに管理対象サーバーを割り当て、「次へ」をクリックします。

5. 環境のマシンを構成し、「次へ」をクリックします。

6. 「サービスのクラスタまたはサーバーへのターゲット設定」画面で環境に定義されているサービスをクラスタにターゲット設定し、「次へ」をクリックします。
注意: WseeJaxwsJmsModule JMSモジュールおよびweblogic.wsee.jaxws.mdb.DispatchPolicyワーク・マネージャは、クラスタ内のすべてのサーバーにターゲット設定してください。

この画面でターゲット設定されたサーバーは、高度なWebサービスで使用するために完全に構成されます。

7. (ステップ9aで選択した場合は)残りの構成画面でその他の情報を構成し、「次へ」をクリックします。

10. 「構成のサマリー」画面が表示されたら、ドメインの詳細を検証して「作成」をクリックします。

Webサービス拡張テンプレートを使用したドメインの拡張

既存のドメインを拡張してこれらのWebサービス機能用に自動的に構成するには:

1. 構成ウィザードを起動します。

2. 「ようこそ」ウィンドウで、「既存のWebLogicドメインの拡張」を選択します。

3. 「次へ」をクリックします。

4. 拡張テンプレートを適用するドメインを選択します。

5. 「次へ」をクリックします。

6. 「次の追加製品をサポートするために、自動的にドメインを拡張する」を選択し、JAX-WS拡張用のWebLogicの高度なWebサービスを選択します。

7. 「次へ」をクリックします。

8. 追加のサーバーおよびクラスタを構成するには:

1. 管理対象サーバーおよびクラスタを定義するには、「オプションの構成を選択」画面で、少なくとも「管理対象サーバー、クラスタ、およびマシン」を選択します。必要に応じて、その他のアイテムを選択し「次へ」をクリックします。

2. 環境の管理対象サーバーを構成し、「次へ」をクリックします。

3. 環境のクラスタを構成し、「次へ」をクリックします。

4. 「クラスタに割当て」画面でクラスタに管理対象サーバーを割り当て、「次へ」をクリックします。

5. 環境のマシンを構成し、「次へ」をクリックします。

6. 「サービスのクラスタまたはサーバーへのターゲット設定」画面で環境に定義されているサービスをクラスタにターゲット設定し、「次へ」をクリックします。
注意: WseeJaxwsJmsModule JMSモジュールおよびweblogic.wsee.jaxws.mdb.DispatchPolicyワーク・マネージャは、クラスタ内のすべてのサーバーにターゲット設定してください。

この画面でターゲット設定されたサーバーは、高度なWebサービスで使用するために完全に構成されます。

7. (ステップ9aで選択した場合は)残りの構成画面でその他の情報を構成し、「次へ」をクリックします。

9. 拡張するドメインが正しいことを確認して「拡張」をクリックします。

10. 終了するには「完了」をクリックします。

Webサービス拡張テンプレートを使用したドメイン拡張でのWLSTの利用

次に、Webサービス拡張テンプレートを使用してドメインを拡張する際にWLSTを使用する方法の例を示します。特にこの例では、単一のサーバー・ドメインを拡張する方法について説明します。すでに単一のサーバー・ドメインを作成済であることを前提としています。次のサンプル・スクリプトで示されている場所に、サーバーおよびクラスタを追加できます。

スクリプトを更新し、ドメインに対して実行したら、すべてのリソースが高度なWebサービス機能用に構成されます。

詳細は、サンプルに記載されているコメントを確認してください。記述されているWLSTコマンドの詳細は、『WebLogic Scripting Toolの理解』を参照してください。

注意:
この例の最後で使用されているwls_webservice_complete_update_utils.pyスクリプトは、Webサービス拡張テンプレートを使用してドメインを拡張する際にドメイン・ディレクトリに追加されます。

例3-1 Webサービス拡張テンプレートを使用したドメイン拡張のためのWLSTスクリプト

# Read the domain.
readDomain(single_server_domain_dir)

# Apply the template to the domain to configure the servers for advanced web service features.
installDir = install_directory/wlserver_10.3
templateLocation = installDir + '/common/templates/applications/wls_webservice_jaxws.jar'
addTemplate(templateLocation)

# Save and close the domain
updateDomain()
closeDomain()

# Read the domain
readDomain(domain_dir)

# Optionally create any servers and clusters required in your domain environment.
# <Include create calls here . . . >
# For example: create('server1','Server') or create('cluster1','Cluster')

# Optionally configure the JMS module as a Uniform Distributed Destination (Recommended)
setDistDestType('WseeJaxwsJmsModule', 'UDD')

# Target WseeJaxwsJmsModule to the desired servers and clusters.
assign('JMSSystemResource', 'WseeJaxwsJmsModule', 'Target', server_or_cluster)
# Repeat assign call for other servers and clusters in the environment.

# Unassign the resource from the Administration Server.
unassign('JMSSystemResource', 'WseeJaxwsJmsModule', 'Target', Administration_Server)

sys.path.append(domain_dir)

# Import the wls_webservice_complete_update_utils.py script. This script is added to the domain directory
# when you extend the domain using the web services extension template.
import wls_webservice_complete_update_utils as update
update.doWseeFixup(globals())

# Save and close the domain
updateDomain()
closeDomain()

ドメインの拡張後に追加されたリソースの更新

JAX-WS拡張用のWebLogicの高度なWebサービス・テンプレートを使用してドメインを作成または拡張した後に、ドメインでリソースを変更すると、次のWLSTスクリプトを使用してこれらのリソースの構成を迅速かつ簡単に更新できます。

スクリプトを更新し、ドメインに対して実行したら、すべてのリソースが高度なWebサービス機能用に構成されます。

注意:
この例の最後で使用されているwls_webservice_complete_update_utils.pyスクリプトは、Webサービス拡張テンプレートを使用してドメインを拡張する際にドメイン・ディレクトリに追加されます。

詳細は、サンプルに記載されているコメントを確認してください。記述されているWLSTコマンドの詳細は、『WebLogic Scripting Toolの理解』を参照してください。

例3-2 ドメインの拡張後に追加されたリソースを更新するためのWLSTスクリプト

# Read the domain.
readDomain(domain_dir)

# Optionally configure the JMS module as a Uniform Distributed Destination (Recommended)
setDistDestType('WseeJaxwsJmsModule', 'UDD')

# Target WseeJaxwsJmsModule to the desired servers and clusters.
assign('JMSSystemResource', 'WseeJaxwsJmsModule', 'Target', server_or_cluster_name)
# Repeat assign call for other servers and clusters in the environment.

# Unassign the resource from the Administration Server.
unassign('JMSSystemResource', 'WseeJaxwsJmsModule', 'Target', Administration_Server_name)

sys.path.append(domain_dir)

# Import the wls_webservice_complete_update_utils.py script. This script is added to the domain
# directory when you extend the domain using the web services extension template.
import wls_webservice_complete_update_utils as update
update.doWseeFixup(globals())

# Save and close the domain.
updateDomain()

WebLogic Advanced Web Services for JAX-WS拡張テンプレートを適用するときの問題に関するトラブルシューティング

WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を使用してドメインを作成または拡張するとき、次に類似したケースとしてfinal.pyスクリプトの実行中に例外が発生する場合があります。

2011-02-24 15:36:26,730 WARN  [Thread-32]
com.oracle.cie.domain.script.ScriptExecutor - warn: set obj126 attribute
Targets to "new_Cluster_1, new_Cluster_2, new_Cluster_3, new_Cluster_4,
new_Cluster_5, new_Cluster_6"
com.oracle.cie.domain.script.ScriptException: Unable to find attribute Targets
...

この問題を回避するには、次の手順に従います。

1. 次のファイルを、WL_HOME/common/templates/applications以外のディレクトリにバックアップします。
WL_HOME/common/templates/applications/wls_webservice_jaxws.jar

たとえば、ファイルをWL_HOME/common/templates/applications/backupにコピーします。

2. script/final.pyファイルをWL_HOME/common/templates/applications/wls_webservice_jaxws.jarファイルから削除します。
Winzipなどのグラフィカル・ツールを使用するか、または次に示すコマンドラインを使用してこれを実行できます。

1. WL_HOME/common/templates/applicationsディレクトリの直下にtempディレクトリを作成します。

2. tempディレクトリにcdします。

3. WL_HOME/common/templates/applications/wls_webservice_jaxws.jarファイル(オリジナル・コピー)をJAR解除します。例:

jar -xvf  ../wls_webservice_jaxws.jar

4. script/final.pyファイルをディレクトリから削除します。

5. オリジナルJARファイルを削除します。例:

rm ../wls_webservice_jaxws.jar

6. wls_webservice_jaxws.jarでJarファイルを作成します。例:

jar cvf  ../wls_webservice_jaxws.jar *

3. 次の手順を実行し、Javaコマンドラインから拡張テンプレートを使用してドメインを拡張します。

1. ドメイン・ディレクトリにcdします。

2. wls_webservice_complete_update.pyスクリプトを実行します。例:

java weblogic.WLST -i wls_webservice_complete_update.py  .

wls_webservice_complete_update.pyスクリプトの詳細は、「高度なWebサービス機能用にドメインを拡張するスクリプト」を参照してください。

Javaから開始するWebLogic Webサービスの開発: 主な手順

この項では、Javaから開始してWebLogic Webサービスを開発する一般的な手順(JWSファイルを最初からコーディングして、サービスについて記述するWSDLファイルを後で生成する手順)について説明します。このプロセスの具体的な例については、第6章「JAX-WS Webサービスの開発例」を参照してください。

次に示すのは推奨の手順にすぎません。独自の開発環境を設定してある場合は、WebLogic Webサービスを開発するために既存の環境を更新する際のガイドとして、この手順を利用できます。

注意:
この手順では、WebLogic Webサービスの分割開発ディレクトリ環境は使用しません。この開発環境を使用していて、Webサービスの開発をそこに統合する場合の詳細は、「WebサービスのWebLogic分割開発ディレクトリ環境への統合」を参照してください。

表3-3 Javaから開始するWebサービスの開発手順

#

手順

説明

1

環境を設定します。

コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)コマンドを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2

プロジェクト・ディレクトリを作成します。

JWSファイル、ユーザー定義のデータ型のJavaソース、Ant build.xmlファイルが格納されるプロジェクト・ディレクトリを作成します。このディレクトリには自由に名前を付けることができます。

3

Webサービスを実装するJWSファイルを作成します。

第4章「JWSファイルのプログラミング」を参照してください。

4

ユーザー定義のデータ型を作成する(オプション)

Webサービスでユーザー定義のデータ型を使用する場合は、その型を記述したJavaBeanを作成します。「ユーザー定義のJavaデータ型のプログラミング」を参照してください。

5

基本のAntビルド・ファイルbuild.xmlを作成します。

「基本的なAnt build.xmlファイルの作成」を参照してください。

6

JWSファイルに対してjwsc Antタスクを実行します。

ソース・コード、データ・バインディング・アーティファクト、デプロイメント記述子などがjwsc Antタスクによって出力ディレクトリ内に生成されます。この出力ディレクトリには、エンタープライズ・アプリケーションのディレクトリ構造も生成されます。この展開されたディレクトリは、後で反復的な開発プロセスの一環としてWebLogic Serverにデプロイします。「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

7

WebサービスをWebLogic Serverにデプロイします。

「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

8

WebサービスのWSDLを参照します。

WebサービスのWSDLを参照して、Webサービスが適切にデプロイされたことを確認します。「WebサービスのWSDLの参照」を参照してください。

9

Webサービスをテストします。

「Webサービスのテスト」を参照してください。

10

Webサービスを編集します。(オプション)

Webサービスに変更を加えるには、JWSファイルを更新し、「WebLogic Webサービスのデプロイとアンデプロイ」の説明のとおりにWebサービスをアンデプロイしてから、jwsc Antタスクの実行(ステップ6)から始まる手順を繰り返します。

Webサービスを呼び出すクライアント・アプリケーションの作成方法については、第8章「Webサービス・クライアントの開発」を参照してください。

WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順

この項では、既存のWSDLファイルに基づいてWebLogic Webサービスを開発する一般的な手順について説明します。このプロセスの具体的な例については、第6章「JAX-WS Webサービスの開発例」を参照してください。

次に示すのは推奨の手順にすぎません。独自の開発環境を設定してある場合は、WebLogic Webサービスを開発するために既存の環境を更新する際のガイドとして、この手順を利用できます。

この手順では既存のWSDLファイルがすでにあることを前提としています。

注意:
この手順では、WebLogic Webサービスの分割開発ディレクトリ環境は使用しません。この開発環境を使用していて、Webサービスの開発をそこに統合する場合の詳細は、「WebサービスのWebLogic分割開発ディレクトリ環境への統合」を参照してください。

表3-4 Javaから開始するWebサービスの開発手順

#

手順

説明

1

環境を設定します。

コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)コマンドを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2

プロジェクト・ディレクトリを作成します。

生成されるアーティファクトやAnt build.xmlファイルが格納されるプロジェクト・ディレクトリを作成します。

3

基本のAntビルド・ファイルbuild.xmlを作成します。

「基本的なAnt build.xmlファイルの作成」を参照してください。

4

WSDLファイルを、build.xml Antビルド・ファイルから読取り可能なディレクトリに置きます。

たとえば、WSDLファイルをプロジェクト・ディレクトリのwsdl_files子ディレクトリに置くことができます。

5

WSDLファイルに対してwsdlc Antタスクを実行します。

JWSサービス・エンドポイント・インタフェース(SEI)、途中まで作成済みのJWSクラス・ファイル、XMLスキーマ・データ型を表すJavaBeanなどが、wsdlc Antタスクによって出力ディレクトリ内に生成されます。「wsdlc WebLogic WebサービスAntタスクの実行」を参照してください。

6

wsdlc Antタスクにより生成された途中まで作成済みのJWSファイルを更新します。

wsdlc Antタスクでは途中まで作成済のJWSファイルが生成されます。Webサービスが希望どおりに動作するようにするには、独自のビジネス・コードを追加する必要があります。「wsdlcで生成される途中まで作成済のJWS実装クラス・ファイルの更新」を参照してください。

7

JWSファイルに対してjwsc Antタスクを実行します。

wsdlc Antタスクによって生成されたアーティファクトと更新したJWS実装ファイルを指定して、Webサービスを実装するエンタープライズ・アプリケーションを生成します。「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

8

WebサービスをWebLogic Serverにデプロイします。

「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

9

WebサービスのWSDLを参照します。

WebサービスのWSDLを参照して、Webサービスが適切にデプロイされたことを確認します。「WebサービスのWSDLの参照」を参照してください。

10

Webサービスをテストします。

「Webサービスのテスト」を参照してください。

11

Webサービスを編集します。(オプション)

Webサービスに変更を加えるには、JWSファイルを更新し、「WebLogic Webサービスのデプロイとアンデプロイ」の説明のとおりにWebサービスをアンデプロイしてから、jwsc Antタスクの実行(ステップ6)から始まる手順を繰り返します。

Webサービスを呼び出すクライアント・アプリケーションの作成方法については、第8章「Webサービス・クライアントの開発」を参照してください。

基本的なAnt build.xmlファイルの作成

Antでは、<project>ルート要素と、Webサービス開発プロセスの様々な段階を指定した1つまたは複数のターゲットが含まれている、XMLで記述されたビルド・ファイル(デフォルト名はbuild.xml)を使用します。各ターゲットには、1つまたは複数のタスク、または実行可能なコードが含まれています。この項では、基本的なAntビルド・ファイルの作成方法について説明し、その後のセクションでは、Webサービス開発プロセスの様々な段階(jwsc Antタスクを実行してJWSファイルを処理する、WebサービスをWebLogic Serverにデプロイする、など)の実行方法を指定したターゲットをビルド・ファイルに追加する方法について説明します。

以下のスケルトンのbuild.xmlファイルでは、以降の項で追加される他のすべてのターゲットを呼び出す、デフォルトのallターゲットを指定しています。

<project default="all">
<target name="all"
depends="clean,build-service,deploy" />
<target name="clean">
<delete dir="output" />
</target>
<target name="build-service">
<!--add jwsc and related tasks here -->
</target>
<target name="deploy">
<!--add wldeploy task here -->
</dftarget>
</project>

開発環境でAntタスクを統合して使用し、Webサービス、およびWebサービスを呼び出すクライアント・アプリケーションをプログラミングする方法の詳細は、次を参照してください。

- 『Oracle WebLogic Server WebLogic Webサービスの理解』のOracle WebLogic ServerのAntタスクの使用に関する項

- 『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のAntタスク・リファレンスの項

- 『Oracle WebLogic Serverアプリケーションの開発』の次の項

- Antタスクを使用したWebLogic Serverドメインの構成と使用に関する項

- wldeploy Antタスクのリファレンスの項

jwsc WebLogic WebサービスAntタスクの実行

jwsc Antタスクは、JWSアノテーションを含むJWSファイルを入力として使用し、WebLogic Webサービスの作成に必要なアーティファクトをすべて生成します。JWSファイルは、最初から自分でコーディングしたものでも、wsdlc Antタスクによって生成されたものでもかまいません。

jwscによって生成されるアーティファクトには、次のものがあります。

- JSR-109 Webサービス・クラス・ファイル。

- JAXBデータ・バインディング・アーティファクト・クラス・ファイル。

- 必要な全デプロイメント記述子。以下を含みます。

- サーブレット・ベースのWebサービス・デプロイメント記述子ファイル(web.xml)。

- Earデプロイメント記述子ファイルapplication.xmlおよびweblogic-application.xml。

注意:
WSDLファイルは、サービス・エンドポイントのデプロイ時に生成されます。

これらのアーティファクトは、wsdlc Antタスクによってすでに生成され、JARファイル内にパッケージ化されているため、wsdlc Antタスクによって生成されたJWSファイルに対してjwsc Antタスクを実行しても、jwscタスクによってはアーティファクトは生成されません。この場合、jwsc Antタスクの属性を使用して、このwsdlc生成JARファイルを指定します。

必要なアーティファクトをすべて生成した後、jwsc Antタスクは、Javaファイル(JWSファイルも含む)をコンパイルし、コンパイルされたクラスと生成されたアーティファクトを、デプロイ可能なJARアーカイブ・ファイルにパッケージ化して、最後に、そのJARファイルを格納する、展開されたエンタープライズ・アプリケーション・ディレクトリを作成します。

jwsc Antタスクには、次のことを可能にする属性および子要素が含まれます。

- 複数のJWSファイルを一度に処理します。生成されたWebサービスをそれぞれ別のWebアプリケーションWARファイルにパッケージ化するか、すべてのWebサービスをグループ化して1つのWARファイルにパッケージ化するかを選択できます。

- クライアント・アプリケーションがWebサービスを呼び出すときに使用できるトランスポート形式(HTTP/HTTPSまたはJMSトランスポート)を指定します(「Webサービスの呼出しに使用されるトランスポートの指定」を参照)。

- 新しいエンタープライズ・アプリケーションまたはWebアプリケーションを生成するのではなく、既存のアプリケーションを更新します。

jwsc Antタスクを実行するには、以下のtaskdefおよびbuild-serviceターゲットをbuild.xmlファイルに追加します。

<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<target name="build-service">
<jwsc
srcdir="src_directory"
destdir="ear_directory"
>
<jws file="JWS_file"
compiledWsdl="WSDLC_Generated_JAR"
type="WebService_type"/>
</jwsc>
</target>

説明:

- ear_directory - 生成されたすべてのアーティファクトを格納するエンタープライズ・アプリケーション・ディレクトリ。

- src_directory - JWSファイルのパッケージ名に対応するサブディレクトリを含む最上位ディレクトリ。

- JWS_file - src_directory属性の値に対して相対的なJWSファイルのパス名。

- WSDLC_Generated_JAR - JWS SEIと、既存のWSDLファイルに対応するデータ・バインディング・アーティファクトが含まれる、wsdlc Antタスクによって生成されたJARファイル。

注意:
この属性は、「WSDLから開始する」ユース・ケースでのみ指定します。この手順は「WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順」で説明されています。

- WebService_type - Webサービスの種類。この値は、JAXWSまたはJAXRPCに設定できます。

必須のtaskdef要素では、jwsc Antタスクの完全修飾クラス名を指定します。

jwsc Antタスクのsrcdirおよびdestdir属性のみが必須です。つまり、デフォルトでは、JWSファイルが参照するJavaファイル(JavaBean入力パラメータやユーザー定義の例外など)はJWSファイルと同じパッケージ内にあると想定されています。これに当てはまらない場合は、sourcepath属性を使用して、これらの他のJavaファイルの最上位ディレクトリを指定します。

jwsc Antタスクの詳細および例については、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のjwscに関する項を参照してください。

Webサービスの呼出しに使用されるトランスポートの指定

jwscの<jws>子要素には、Webサービスの呼出しに使用するトランスポート(HTTP/SまたはJMS)を指定するための、次に示すオプションの子要素があります。

- WLHttpTransport: 生成されたWSDLのポート名に加え、HTTP/SトランスポートでWebサービスを呼び出すために使用するコンテキスト・パスおよびURLのサービスURIセクションを指定します。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWLHttpTransportに関する項を参照してください。

- JmsTransportService: SOAP over JMSトランスポートを有効化および構成します。必要に応じて、宛先名、宛先タイプ、配信モード、リクエストおよびレスポンス・キューなどのJMSトランスポート・プロパティを構成できます。詳細は、第3章「JAX-WS Webサービスの開発」を参照してください。

次のガイドラインで、jwsc Antタスクのトランスポート要素の使用方法について説明します。

- jwscに対して指定したトランスポートは、JWSファイル内のすべての対応するトランスポート・アノテーションを常にオーバーライドします。また、トランスポート要素の対応する属性を明示的に指定していない場合でも、トランスポート・アノテーションのすべての属性は無視されます。この場合、トランスポート要素属性のデフォルト値が使用されます。

- 特定のJWSファイルに対して両方のトランスポート要素を指定できます。ただし、指定できるのは、特定のトランスポート要素の1つのインスタンスのみです。たとえば、特定のJWSファイルに2つの異なる<WLHttpTransport>要素を指定することはできませんが、<WLHttpTransport>要素と<WLJmsTransport>要素をそれぞれ1つずつ指定することはできます。

- serviceURI属性の値は、<WLJMSTransport>と<WLHttpTransport>の両方を指定する際、同じにすることができます。

- 特定のJWSファイルに関連付けられるすべてのトランスポートでは、同じcontextPath属性値を指定する必要があります。

- 特定のJWSファイルに複数のトランスポート要素を指定する場合、各要素のportName属性の値は、すべての要素において一意である必要があります。つまり、複数のトランスポート子要素を<jws>に追加する場合、この属性を明示的に指定する必要があることを意味します。これは、要素のデフォルト値は常に同じになるため、jwsc Antタスクの実行時にエラーが発生するためです。

- jwsc Antタスクに対するトランスポート要素のいずれかまたはJWSファイルのトランスポート・アノテーションとしてトランスポートを指定しなかった場合、WebサービスのデフォルトURLは、WLHttpTransport要素のデフォルト値と一致します。

WebLogic Webサービスのコンテキスト・パスの定義

WebLogic Webサービスのコンテキスト・パス(コンテキスト・ルートとも呼ばれます)は、様々な場所で指定できます。この項では、サービスのコンテキスト・パスが複数の場所で設定されている場合でも、構成に基づいてサービスの正しいコンテキスト・パスを判別する方法について説明します。

この説明では、Webサービスのコンテキスト・パスとは、WebサービスURLのhost:port部分の後にくる文字列を指します。たとえば、WebLogic WebサービスのデプロイされたWSDLが次のとおりであるとします。

http://hostname:7001/financial/GetQuote?WSDL

financialが、このWebサービスのコンテキスト・パスです。

次に、コンテキスト・パスを指定できるすべての場所の優先順位を、重要度の高い順番で示します。

1. <module>要素および<jws>要素のcontextPath属性(jwsc Antタスクの直接の子として使用される場合)

2. <jws>の<WLHttpTransport>子要素のcontextPath属性

3. コンテキスト・パスのデフォルト値(JWSファイルの名前。ただし、拡張子は付きません)

そのbuild.xmlファイルを更新し、<WLHttpTransport>子要素をJWSファイルを指定する<jws>要素に追加し、そのcontextPath属性をfinanceに設定するものと仮定します。今度は、Webサービスのコンテキスト・パスはfinanceになります。ただし、次に<module>要素の下で<jws>要素とその子<WLHttpTransport>要素をグループ化し、そのcontextPath属性をmoneyに設定すると、Webサービスのコンテキスト・パスはmoneyになります。

JWSファイルまたはjwsc AntタスクにおいてcontextPath属性を1つも指定しない場合、Webサービスのコンテキスト・パスはデフォルト値(*.java拡張子の付かないJWSファイルの名前)になります。

複数の<jws>要素を1つの<module>要素の下でグループ化し、前述の他のオプションを使用してコンテキスト・パスを設定しない場合、<module>のcontextPath属性で、モジュール内のすべてのWebサービスで使用される共通のコンテキスト・パスを指定する必要があります。そうしないと、モジュール内のすべてのWebサービスのデフォルト・コンテキスト・パスが異なってしまいます(実装するJWSファイルの名前が異なることに起因します)が、1つのWARファイル内で異なるコンテキスト・パスを使用することはできません。

jwscの使用例

以下のbuild.xmlの抜粋では、JWSファイルに対してjwsc Antタスクを実行する基本的な例を示します。

<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<target name="build-service">
<jwsc
srcdir="src"
destdir="output/helloWorldEar">
<jws
file="examples/webservices/hello_world/HelloWorldImpl.java"
type="JAXWS"/>
</jwsc>
</target>

この例では、

- カレント・ディレクトリに対して相対的なoutput/helloWorldEarに、エンタープライズ・アプリケーションが展開形式で生成されます。

- JWSファイルはHelloWorldImpl.javaという名前で、カレント・ディレクトリに対して相対的なsrc/examples/webservices/hello_worldディレクトリにあります。つまり、JWSファイルはパッケージexamples.webservices.helloWorld内にあります。

- JAX-WS Webサービスが生成されます。

以下の例は前の例と似ていますが、compiledWsdl属性を使用して、wsdlcが生成したアーティファクト(「WSDLから開始する」ユース・ケース)を含むJARファイルを指定している点が異なります。

<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<target name="build-service">
<jwsc
srcdir="src"
destdir="output/wsdlcEar">
<jws
file="examples/webservices/wsdlc/TemperaturePortTypeImpl.java"
compiledWsdl="output/compiledWsdl/TemperatureService_wsdl.jar"
type="JAXWS"/>
</jwsc>
</target>

この例では、TemperaturePortTypeImpl.javaファイルが、独自のビジネス・ロジックを含めて更新した、途中まで作成されていたJWSファイルです。compiledWsdl属性が指定されてJARファイルを指し示しているので、jwsc Antタスクでは、JARに含まれているアーティファクトを再生成することはありません。

このタスクを実際に実行するには、コマンド・ラインで次のように入力します。

prompt> ant build-service

wsdlc WebLogic WebサービスAntタスクの実行

wsdlc AntタスクはWSDLファイルを入力として処理し、WebLogic Webサービスの実装を構成するアーティファクトを生成します。次のようなアーティファクトがあります。

- WSDLファイルで記述されたWebサービスを実装するJWSサービス・エンドポイント・インタフェース(SEI)。

- 生成されるJWS SEIの不完全な(途中まで作成済みの)実装が含まれるJWS実装ファイル。このファイルは開発者がカスタマイズする必要があります。

- JAXBデータ・バインディング・アーティファクト。

- (オプション)生成されるJWS SEIのJavadoc。

wsdlc AntタスクはJWS SEIとデータ・バインディング・アーティファクトを一緒にJARファイルにパッケージ化します。このJARファイルを後でjwsc Antタスクに指定します。このJARファイルを更新する必要はありません。更新するファイルはJWS実装クラスのみです。

wsdlc Antタスクを実行するには、以下のtaskdefおよびgenerate-from-wsdlターゲットをbuild.xmlファイルに追加します。

<taskdef name="wsdlc"
classname="weblogic.wsee.tools.anttasks.WsdlcTask"/>
<target name="generate-from-wsdl">
<wsdlc
srcWsdl="WSDLFile"
destJwsDir="JWS_interface_directory"
destImplDir="JWS_implementation_directory"
packageName="Package_name"
type="WebService_type"/>
</target>

説明:

- WSDLFile - 部分的な実装を生成する元となるWSDLファイルの名前(絶対パスまたは相対パスを含める)。

- JWS_interface_directory - JWS SEIおよびデータ・バインディング・アーティファクトを含むJARファイルの生成先となるディレクトリ。
生成されるJARファイルの名前はWSDLFile_wsdl.jarです(WSDLFileはWSDLファイルのルート名)。たとえば、file属性に対して指定したWSDLファイルの名前がMyService.wsdlの場合、生成されるJARファイルはMyService_wsdl.jarとなります。

- JWS_implementation_directory - 途中まで作成済みのJWS実装ファイルの生成先となる最上位ディレクトリ。ファイルはパッケージ名に対応するサブディレクトリ階層に生成されます。
生成されるJWSファイルの名前はService_PortTypeImpl.javaです。ServiceとPortTypeはそれぞれ、Webサービスを生成しているWSDLファイル内の<service>要素およびその内部の<port>要素のname属性を指します。たとえば、サービス名がMyServiceで、ポート名がMyServicePortTypeの場合、JWS実装ファイルの名前はMyService_MyServicePortTypeImpl.javaとなります。

- Package_name - 生成されるJWS SEIおよび実装ファイルの生成先となるパッケージ。この属性を指定しない場合、wsdlc Antタスクは、WSDLのtargetNamespaceに基づいてパッケージ名を生成します。

- WebService_type - Webサービスの種類。この値は、JAXWSまたはJAXRPCに設定できます。

必須のtaskdef要素では、wsdlc Antタスクの完全修飾クラス名を指定します。

wsdlc Antタスクでは、srcWsdlおよびdestJwsDir属性のみが必須です。ただし、通常は、プログラミングを容易にするために、途中まで作成済みのJWSファイルを生成します。WSDLファイルのtargetNamespaceが、読取り可能なパッケージ名への変換に適していない場合に備えて、パッケージ名を明示的に指定することをお薦めします。

以下のbuild.xmlの抜粋では、WSDLファイルに対してwsdlc Antタスクを実行する例を示します。

<taskdef name="wsdlc"
classname="weblogic.wsee.tools.anttasks.WsdlcTask"/>
<target name="generate-from-wsdl">
<wsdlc
srcWsdl="wsdl_files/TemperatureService.wsdl"
destJwsDir="output/compiledWsdl"
destImplDir="impl_output"
packageName="examples.webservices.wsdlc"
type="JAXWS" />
</target>

この例では、

- 既存のWSDLファイルはTemperatureService.wsdlという名前で、build.xmlファイルを格納するディレクトリのwsdl_filesサブディレクトリにあります。

- JWS SEIとデータ・バインディング・アーティファクトを含むJARファイルはoutput/compiledWsdlディレクトリに生成され、JARファイルの名前はTemperatureService_wsdl.jarです。

- 生成されるJWSファイルのパッケージ名はexamples.webservices.wsdldです。

- 途中まで作成済みのJWSファイルは、カレント・ディレクトリに対して相対的なimpl_output/examples/webservices/wsdlcディレクトリに生成されます。

- WSDLファイルのサービス名およびポート・タイプ名がそれぞれTemperatureServiceおよびTemperaturePortTypeであり、JWS実装ファイルの名前がTemperatureService_TemperaturePortTypeImpl.javaであるものとします。

- JAX-WS Webサービスが生成されます。

このタスクを実際に実行するには、コマンド・ラインで次のように入力します。

prompt> ant generate-from-wsdl

詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のwsdlcに関する項を参照してください。

wsdlcで生成される途中まで作成済みのJWS実装クラス・ファイルの更新

wsdlc Antタスクは、destImplDir属性で指定されたディレクトリに、途中まで作成済のJWS実装ファイルを生成します。ファイルの名前はService_PortTypeImpl.javaで、Serviceは元のWSDLファイル内のサービスの名前、PortTypeはポート・タイプ名です。このクラス・ファイルには、独自のビジネス・ロジックを除いて、Webサービスへコンパイルするために必要なすべてのものが含まれています。

JWSクラスは、WSDLファイルに対応するJWS Webサービス・エンドポイント・インタフェースを実装しています。このJWS SEIもwsdlcによって生成され、他のアーティファクト(WSDL内のXMLスキーマ・データ型のJava表現など)が含まれているJARファイル内に置かれています。JWSクラスのパブリック・メソッドはWSDLファイル内の操作に対応しています。

wsdlc Antタスクは、JWS実装クラスに@WebServiceアノテーションを自動的に含めます。属性の値は、WSDL内の関連する値に対応しています。たとえば、@WebServiceのserviceName属性は、WSDLファイル内の<service>要素のname属性と同じです。

JWSファイルを更新するときは、該当のWebサービス操作が希望どおりに動作するように、メソッドにJavaコードを追加します。通常、生成されるJWSファイルには、コードを追加すべき場所に次のようなコメントがあります。

//replace with your impl here

また、他のJWSアノテーションをファイルに追加することもできますが、以下のような制限があります。

- JWS実装ファイルに含めることができる標準(JSR-181)のjavax.jwsパッケージのアノテーションは、@WebService、@HandlerChain、@SOAPMessageHandler、および@SOAPMessageHandlersのみです。javax.jwsパッケージの他のJWSアノテーションを指定し、JWSファイルをWebサービスにコンパイルしようとすると、jwsc Antタスクはエラーを返します。たとえば、JWS実装ファイルに@Policyアノテーションを指定すると、jwsc Antタスクはコンパイル・エラーを返します。

- @WebServiceアノテーションでは、serviceName、endpointInterface、およびtargetNamespace属性のみを指定できます。まれに、WSDLファイルに複数の<service>要素が指定されていることがあります。その場合は、serviceName属性を使用して、wsdlc Antタスクで使用していたものとは別の<service> WSDL要素を指定します。wsdlc Antタスクで生成されたJWS SEIを指定するには、endpointInterface属性を使用します。WSDLサービスのネームスペースを指定するには、targetNamespace属性を使用します。JWS SEIネームスペースと異なるネームスペースを指定できます。

- 必要に応じて、JAX-WS-JSR 224、JAXB (JSR 222)または共通アノテーション(JSR 250)を指定できます。サポートされる各アノテーションの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のJWSアノテーション・リファレンスに関する項を参照してください。

JWSファイルを更新したら、wsdlcの出力ディレクトリにそのまま置いておかないで、正式なソースの場所に移動することをお薦めします。

次の例は、「サンプルWSDLファイル」のWSDLからwsdlcが生成したJWS実装ファイルです。太字のテキストは、Webサービスの1つの操作(getTemp)を実装するJavaコードを追加する場所を示しています。

package examples.webservices.wsdlc;
import javax.jws.WebService;
/**
* TemperaturePortTypeImpl class implements web service endpoint interface
* TemperaturePortType */
@WebService(
serviceName="TemperatureService",
endpointInterface="examples.webservices.wsdlc.TemperaturePortType")
public class TemperaturePortTypeImpl implements TemperaturePortType {
public TemperaturePortTypeImpl() {
}
public float getTemp(java.lang.String zipcode)
{
//replace with your impl here
return 0;
}
}

WebLogic Webサービスのデプロイとアンデプロイ

Webサービスはエンタープライズ・アプリケーションとしてパッケージ化されるので、Webサービスのデプロイとは、該当するEARファイルまたは展開されたディレクトリをデプロイすることになります。

WebLogic Server管理コンソールの使用からweblogic.Deployer Javaユーティリティの使用まで、WebLogicアプリケーションのデプロイには多様な方法があります。開発環境とは異なり、本番環境にアプリケーションをデプロイする際には、他にも様々な問題を考慮する必要があります。デプロイメントの詳細は、『Oracle WebLogic Serverへのアプリケーションのデプロイ』を参照してください。

このガイドでは、開発の性質上、Webサービスの2つのデプロイ方法についてのみ説明します。

- wldeploy Antタスクを使用したWebサービスのデプロイ

- 管理コンソールを使用したWebサービスのデプロイ

wldeploy Antタスクを使用したWebサービスのデプロイ

反復的な開発プロセスの一環としてWebサービスをデプロイする最も簡単な方法は、wldeploy WebLogic Antタスクを実行するターゲットを、jwsc Antタスクが含まれる同じbuild.xmlファイルに追加することです。Javaコードを追加してサービスを再生成するたびに、サービスの再デプロイとテストを繰返し行えるように、Webサービスをデプロイするタスクとアンデプロイするタスクの両方を追加することができます。

wldeploy Antタスクを使用するには、以下のターゲットをbuild.xmlファイルに追加します。

<target name="deploy">
<wldeploy action="deploy"
name="DeploymentName"
source="Source" user="AdminUser"
password="AdminPassword"
adminurl="AdminServerURL"
targets="ServerName"/>
</target>

説明:

- DeploymentName - エンタープライズ・アプリケーションのデプロイメント名、または、WebLogic Server管理コンソールでデプロイメントのリストに表示される名前。

- Source - デプロイするエンタープライズ・アプリケーションのEARファイルまたは展開されたディレクトリの名前。デフォルトでは、jwsc Antタスクが展開されたエンタープライズ・アプリケーション・ディレクトリを生成します。

- AdminUser - 管理ユーザー名。

- AdminPassword - 管理パスワード。

- AdminServerURL - 管理サーバーのURL。通常はt3://localhost:7001です。

- ServerName - WebサービスをデプロイするWebLogic Serverインスタンスの名前。

たとえば、以下のwldeployタスクでは、エンタープライズ・アプリケーションの展開されたディレクトリ(カレント・ディレクトリに対して相対的なoutput/ComplexServiceEarにある)がmyServer WebLogic Serverインスタンスにデプロイされることを指定します。デプロイメント名はComplexServiceEarです。

<target name="deploy">
<wldeploy action="deploy"
name="ComplexServiceEar"
source="output/ComplexServiceEar" user="weblogic"
password="weblogic" verbose="true"
adminurl="t3://localhost:7001"
targets="myserver"/>
</target>

Webサービスを実際にデプロイするには、コマンドラインでdeployターゲットを実行します。

prompt> ant deploy

ソース・コードに変更を加えてからWebサービスを再デプロイできるように、Webサービスを簡単にアンデプロイするターゲットを追加することもできます。

<target name="undeploy">
<wldeploy action="undeploy"
name="ComplexServiceEar"
user="weblogic"
password="weblogic" verbose="true"
adminurl="t3://localhost:7001"
targets="myserver"/>
</target>

Webサービスをアンデプロイするときは、source属性を指定する必要はなく、名前によってアンデプロイします。

管理コンソールを使用したWebサービスのデプロイ

WebLogic Server管理コンソールを使用してWebサービスをデプロイするには、最初に、ブラウザで次のURLを使用してWebサービスを呼び出します。

http://[host]:[port]/console

説明:

- host WebLogic Serverが動作しているコンピュータの名前。

- port - WebLogic Serverがリスニングしているポート番号(デフォルト値は7001です)。

次にデプロイメント・アシスタントを使用して、エンタープライズ・アプリケーションをデプロイします。WebLogic Server管理コンソールの詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプを参照してください。

WebサービスのWSDLの参照

WebサービスのWSDLをブラウザで表示して、Webサービスが適切にデプロイされていることを確認できます。

次のURLは、WebサービスのWSDLをブラウザで表示する方法を示しています。

http://[host]:[port]/[contextPath]/[serviceUri]?WSDL

説明:

- host - WebLogic Serverが動作しているコンピュータの名前(localhostなど)。

- port - WebLogic Serverがリスニングしているポート番号(デフォルト値は7001です)。

- contextPath - Webサービスのコンテキスト・ルート。コンテキスト・ルートを設定する場所としては、jwscの<WLHttpTransport>、<module>、または<jws>要素があり、オーバーライドの順位が決まっています。「WebLogic Webサービスのコンテキスト・パスの定義」を参照してください。

- serviceUri - jwsc Antタスクの<WLHttpTransport>子要素のserviceUri 属性の値。jwsc AntタスクでserviceUri属性のいずれかを指定しない場合、WebサービスのserviceUriはデフォルト値(@WebServiceアノテーションのserviceName要素)になります。逆の場合、拡張子を除いたJWSファイルの名前の後にServiceを付けたものになります。

たとえば、次のようにWebサービスの構築に使用するjwscタスクで<WLHttpTransport>子要素を指定したものとします。

<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}"
keepGenerated="true">
<jws file="examples/webservices/complex/ComplexImpl.java"
type="JAXWS">
<WLHttpTransport
contextPath="complex" serviceUri="ComplexService"
portName="ComplexServicePort"/>
</jws>
</jwsc>
</target>

そして、Webサービスがarielというホストのデフォルトのポート番号(7001)で実行されているとすると、そのWebサービスのWSDLを表示するURLは次のようになります。

http://ariel:7001/complex/ComplexService?WSDL

動的なWSDLで指定されたサーバー・アドレスの構成

デプロイ済のWebサービスのWSDL(動的なWSDLともいいます)には、特定のWebサービス・ポートにアドレス(URI)を割り当てる<address>要素が含まれています。たとえば、次に示すWSDLの抜粋には、ComplexServiceというデプロイ済のWebLogic Webサービスの一部が記述されています。

<definitions name="ComplexServiceDefinitions"
targetNamespace="http://example.org">
...
<service name="ComplexService">
<port binding="s0:ComplexServiceSoapBinding" name="ComplexServicePort">
<s1:address location="http://myhost:7101/complex/ComplexService"/>
</port>
</service>
</definitions>

この例では、ComplexService WebサービスにComplexServicePortというポートが含まれており、そのアドレスはhttp://myhost:7101/complex/ComplexServiceとなっています。

WebLogic Serverは、このアドレスのcomplex/ComplexServiceの部分を、jwsc要素のcontextPathおよびserviceURI属性を調べることによって決定します(「WebサービスのWSDLの参照」に説明があります)。しかし、WebLogic Serverがアドレスのプロトコルおよびホスト部分(この例ではhttp://myhost:7101)を決定するために使用する方法は、次で説明するとおり、より複雑です。この項では、わかりやすいように、アドレスのプロトコルとホストの部分をまとめてサーバー・アドレスと呼ぶことにします。

WebLogic Serverがデプロイ済のWebサービスの動的なWSDL内にパブリッシュするサーバー・アドレスは、そのWebサービスをHTTP/SやJMSで呼び出せるかどうか、プロキシ・サーバーを構成しているかどうか、Webサービスがクラスタにデプロイされているかどうか、Webサービスが実際にはコールバック・サービスであるかどうかによって異なります。

以下では、これらの構成の違いに応じたサーバー・アドレスの決定方法について説明します。また、ニーズに合わせて構成を変更するための手順説明へのリンクも示します。

- Webサービスがコールバック・サービスでなく、HTTP/Sを使用して呼び出せる場合

- Webサービスがコールバック・サービスである場合

- Webサービスがプロキシ・サーバーを使用して呼び出せる場合

なお、ここでは、クラスタとスタンドアロン・サーバーを、WebLogic Server管理コンソールを使用して構成することを前提としています。

Webサービスがコールバック・サービスでなく、HTTP/Sを使用して呼び出せる場合

- Webサービスがクラスタにデプロイされる場合、動的WSDLのサーバー・アドレスには次の値(優先度の高い順になっています)が使用されます。

- 構成済ネットワーク・チャネル(「ネットワーク・チャネルを使用したフロントエンドSOAPルーターのIDの構成」を参照)。

- クラスタ用に構成されたFrontend Host、Frontend HTTP PortおよびFrontend HTTPS Port(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタ用のHTTP設定の構成に関する項を参照)

- ローカル・サーバー用に構成されたFrontend Host、Frontend HTTP PortおよびFrontend HTTPS Port(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのHTTPプロトコルの構成に関する項を参照)

- 前述のアイテムがいずれも設定されていない場合は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタの構成に関する項の説明のとおり、クラスタに対してCluster Addressを設定する必要があります。WSDLに表示されるクラスタ・アドレスの生成には、リクエストURLからの指定プロトコル(httpなど)のサーバー・チャネルが使用されます。

- Webサービスが個々のサーバーにデプロイされる場合、ローカル・サーバー用に構成されたFrontend Host、Frontend HTTP PortおよびFrontend HTTPS Portが動的WSDLのサーバー・アドレスで使用されます(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのHTTPプロトコルの構成に関する項を参照)。

Webサービスがコールバック・サービスである場合

1. コールバック・サービスがクラスタにデプロイされる場合、動的WSDLのサーバー・アドレスには次の値(優先度の高い順になっています)が使用されます。

- 構成済ネットワーク・チャネル(「ネットワーク・チャネルを使用したフロントエンドSOAPルーターのIDの構成」を参照)。

- クラスタ用に構成されたFrontend Host、Frontend HTTP PortおよびFrontend HTTPS Port(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタ用のHTTP設定の構成に関する項を参照)

- ローカル・サーバー用に構成されたFrontend Host、Frontend HTTP PortおよびFrontend HTTPS Port(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのHTTPプロトコルの構成に関する項を参照)

- クラスタのCluster Address(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタの構成に関する項を参照)。Cluster Addressは、他の値が設定されていない場合に必要となります。

2. コールバック・サービスが個々のサーバーにデプロイされる場合、ローカル・サーバー用に構成されたFrontend Host、Frontend HTTP PortおよびFrontend HTTPS Portが動的WSDLのサーバー・アドレスで使用されます(Oracle WebLogic Server管理コンソール・オンライン・ヘルプのHTTPプロトコルの構成に関する項を参照)。

3. 上記のどの値も設定されていないが、コールバック・サービスがデプロイされているサーバーのListen Addressが設定されている場合は、サーバー・アドレスにこの値が使用されます。
Oracle WebLogic Server管理コンソール・オンライン・ヘルプのリスニング・アドレスの構成に関する項を参照してください。

Webサービスがプロキシ・サーバーを使用して呼び出せる場合

必須ではありませんが、Webサービスがデプロイされているクラスタまたは個々のサーバーのFrontend Host、FrontEnd HTTP Port、およびFrontend HTTPS Portがプロキシ・サーバーを指すように明示的に設定することをお薦めします。

Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタのHTTP設定の構成に関する項またはHTTPプロトコルの構成に関する項を参照してください。

Webサービスのテスト

WebLogic Webサービスをデプロイすると、セキュリティ、サービス品質(QoS)、HTTPヘッダーなど、Webサービスの基本機能および高度な機能をテストできます。セキュリティ機能のストレス・テストを実行することもできます。Webサービス・テスト・クライアントまたはFusion Middleware Controlの「Webサービスのテスト」ページを使用したWebサービスのテストの詳細は、『Webサービスの管理』のWebサービスのテストに関する項を参照してください。

WebサービスのWebLogic分割開発ディレクトリ環境への統合

この項では、Webサービスの開発をWebLogic分割開発ディレクトリ環境に統合する方法について説明します。このWebLogic機能について理解していること、標準のJava Platform, Enterprise Edition (Java EE)バージョン5アプリケーションおよびモジュール(EJBやWebアプリケーションなど)の開発用にこのタイプの環境を設定済であること、Webサービスの開発が含まれるようにbuild.xmlファイルの更新を計画していることを前提としています。

WebLogic分割開発ディレクトリ環境の詳細は、『Oracle WebLogic Serverアプリケーションの開発』の分割開発ディレクトリ環境の作成に関する項およびWebLogic Serverと一緒にインストールされるsplitdir/helloWorldEarサンプルを参照してください(サンプルは、EXAMPLES_HOME/wl_server/examples/src/examplesディレクトリにあります。ここでEXAMPLES_HOMEはWebLogic Serverコード・サンプルが構成されているディレクトリです)。詳細は、『Oracle WebLogic Serverの理解』のサンプル・アプリケーションおよびサンプル・コードに関する項を参照してください。

1. メイン・プロジェクト・ディレクトリ内に、Webサービスを実装するJWSファイルを格納するためのディレクトリを作成します。
たとえば、メイン・プロジェクト・ディレクトリが/src/helloWorldEarである場合、/src/helloWorldEar/helloWebServiceというディレクトリを作成します。

prompt> mkdir /src/helloWorldEar/helloWebService

2. helloWebServiceディレクトリの下に、JWSファイルのパッケージ名に対応するディレクトリ階層を作成します。
たとえば、JWSファイルがexamples.splitdir.helloパッケージにパッケージ化されている場合は、examples/splitdir/helloというディレクトリ階層を作成します。

prompt> cd /src/helloWorldEar/helloWebService
prompt> mkdir examples/splitdir/hello

3. メイン・プロジェクト・ディレクトリに作成したWebサービスのサブディレクトリ(この例では/src/helloWorldEar/helloWebService/examples/splitdir/hello)にJWSファイルを置きます。

4. エンタープライズ・アプリケーションをビルドするbuild.xmlファイル内に、「jwsc WebLogic WebサービスAntタスクの実行」の説明に従ってjwsc WebLogic WebサービスAntタスクの呼出しを追加して、Webサービスをビルドする新しいターゲットを作成します。
jwscのsrcdir属性は、JWSファイルを格納する最上位ディレクトリ(この例ではhelloWebService)を指すようにします。jwscのdestdir属性は、wlcompileに指定するのと同じ宛先ディレクトリを指すようにします。次の例を参照してください。

<target name="build.helloWebService">
<jwsc
srcdir="helloWebService"
destdir="destination_dir"
keepGenerated="yes" >
<jws file="examples/splitdir/hello/HelloWorldImpl.java"
type="JAXWS" />
</jwsc>
</target>

この例のdestination_dirは、他の分割開発ディレクトリ環境のAntタスク(wlappcやwlcompileなど)も使用する宛先ディレクトリを表します。

5. Webサービス関連のターゲットを呼び出すように、build.xmlファイルのメインのbuildターゲットを更新します。

<!-- Builds the entire helloWorldEar application -->
<target name="build"
description="Compiles helloWorldEar application and runs appc"
depends="build-helloWebService,compile,appc" />

注意:
エンタープライズ・アプリケーションを実際にビルドするときは、wlappc Antタスクを実行する前に、jwsc Antタスクを実行するようにしてください。wlappcを正常に実行するには、jwscによって生成されるアーティファクトの一部が必要になるためです。この例の場合は、appcターゲットよりも前にbuild-helloWebServiceターゲットを指定する必要があります。

6. wlcompileおよびwlappc Antタスクを使用してエンタープライズ・アプリケーション全体をコンパイルおよび検証する場合は、両方のAntタスクでWebサービスのソース・ディレクトリを除外するようにしてください。これは、jwsc AntタスクでWebサービスのコンパイルとパッケージ化をすでに扱っているためです。例:

<target name="compile">
<wlcompile srcdir="${src.dir}" destdir="${dest.dir}"
excludes="appStartup,helloWebService">
...
</wlcomplile>
...
</target>
<target name="appc">
<wlappc source="${dest.dir}" deprecation="yes" debug="false"
excludes="helloWebService"/>
</target>

7. META-INFプロジェクト・ソース・ディレクトリにあるapplication.xmlファイルを更新して、<web>モジュールを追加し、jwsc Antタスクによって生成されるWARファイルの名前を指定します。
たとえば、helloWorld Webサービスのapplication.xmlファイルに次のように追加します。

<application>
...
<module>
<web>
<web-uri>examples/splitdir/hello/HelloWorldImpl.war</web-uri>
<context-root>/hello</context-root>
</web>
</module>
...
</application>

注意:
jwsc Antタスクでは通常、Webサービスを実装するJWSファイルからWebアプリケーションWARファイルが生成されます。ただし、JWSファイルに@Statelessアノテーションを使用してEJBを定義されている場合は例外です。その場合は、application.xmlファイルに<ejb>モジュール要素を追加する必要があります。

これで、分割開発ディレクトリ環境は、Webサービスの開発を含むように更新されました。エンタープライズ・アプリケーション全体を再ビルドしてデプロイするときに、WebサービスもEARの一部としてデプロイされます。Webサービスは、「WebサービスのWSDLの参照」で説明されている標準的な方法で呼び出します。

4 JWSファイルのプログラミング

この章では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスを実装するJWSファイルのプログラミング方法について説明します。

この章の内容は次のとおりです。

- JWSファイルとJWSアノテーションの概要

- JWSファイルのJava要件

- JWSファイルのプログラミング: 一般的な手順

- Webサービスの実行時情報へのアクセス

- ステートレスまたはシングルトン・セッションEJBを実装すべき場合

- ユーザー定義のJavaデータ型のプログラミング

- JWSファイルからの別のWebサービスの呼出し

- SOAP 1.2の使用

- XMLスキーマの検証

- JWSプログラミングのベスト・プラクティス

JWSファイルとJWSアノテーションの概要

WebLogic Webサービスをゼロからプログラミングする方法は2つあります。

1. JSR-181、JAX-WS仕様、およびWebLogic Webサービス・プログラミング・モデルで規定されているように、標準のEJBまたはJavaクラスにWebサービスJavaアノテーションを付けます。

2. デプロイメント記述子、WSDLファイル、データ・マッピング記述子、データ・バインディング・アーティファクト(ユーザー定義のデータ型用)など、JSR-109で指定されている様々なXML記述子ファイルやアーティファクトと、標準のEJBまたはJavaクラスを結合します。

Oracleでは、上記のオプション1を実行することを強くお薦めします。ユーザー自身がXMLメタデータ記述子を作成しなくても、必要な記述子やアーティファクトはJWSにユーザーが含めたアノテーションに基づいてWebLogic Antタスクおよびランタイムによって生成されます。このプロセスの方がはるかに簡単なだけでなく、Webサービスの情報が多数のJavaファイルやXMLファイル内に分散されず、JWSファイルで集中管理されます。

アノテーション付きのJava Webサービス(JWS)ファイルは、Webサービスの中核部分です。このファイルにはWebサービスの動作を決定するJavaコードが含まれています。JWSファイルは、Javaメタデータ・アノテーションを使用してWebサービスの形式や特性を指定した、通常のJavaクラス・ファイルです。JWSファイルでは、Web Services Metadata for the Java Platform仕様(JSR-181)(http://www.jcp.org/en/jsr/detail?id=181を参照)で定義される標準的なJWSアノテーションに加え、作成中のWebサービスの種類(JAX-WSまたはJAX-RPC)に基づいたその他のアノテーション・セットの使用が可能です。JAX-WS WebサービスおよびJAX-RPC Webサービスに対してサポートされているJWSアノテーションの完全なリストについては、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスのアノテーション・サポートに関する項を参照してください。

JWSファイルをプログラミングする際は、基本的なWebサービス機能をプログラミングするためにアノテーションを含めます。アノテーションは、JWSファイル内の様々なレベル、様々なターゲットで使用されます。一部のアノテーションは、JWSファイル全体に適用されることを示すためにクラス・レベルで使用されます。それ以外のアノテーションには、メソッド・レベルで使用するものや、パラメータ・レベルで使用するものがあります。

JWSファイルのJava要件

JWSファイルをプログラミングする場合は、Web Services Metadata for the Java Platform仕様(JSR-181)(http://www.jcp.org/en/jsr/detail?id=181)で指定された一連の要件に従う必要があります。特に、Webサービスを実装するJavaクラスは、次の要件に従う必要があります。

- パブリック・クラスでなければなりません。finalクラスやabstractクラスとして宣言することはできません。

- デフォルトのパブリック・コンストラクタを持つ必要があります。

- finalize()メソッドは定義できません。

- 少なくとも、クラス・レベルで@WebService JWSアノテーションを指定して、そのJWSファイルがWebサービスを実装することを指定する必要があります。

- @WebService.endpointInterfaceアノテーションを使用して、サービス・エンドポイント・インタフェースを参照できます。この場合は、サービス・エンドポイント・インタフェースが存在することを前提としています。JWSファイルでは@WebService.endpointInterface、@WebService.serviceNameおよび@WebService.targetNamespace以外のJWSアノテーションを指定することはできません。

- JWSファイルにサービス・エンドポイント・インタフェースが実装されていない場合は、java.lang.Objectから継承されたもの以外のすべてのパブリック・メソッドが、Webサービス操作として公開されます。この動作は、@WebMethodアノテーションを使用して、公開するパブリック・メソッドを明示的に指定することによって、オーバーライドできます。@WebMethodアノテーションが存在する場合は、それが適用されるメソッドのみが公開されます。

JWSファイルのプログラミング: 一般的な手順

次の手順では、Webサービスを実装するJWSファイルをプログラミングするための一般的な手順を説明します。

注意:
JWSファイルを作成してあり、そこにJWSアノテーションを追加する予定であることを前提としています。

各JWSアノテーションの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のJWSアノテーション・リファレンスに関する項を参照してください。

表4-1 JWSファイルのプログラミング手順

#

手順

説明

1

JWSファイルで使用する標準のJWSアノテーションをインポートします。

標準のJWSアノテーションはjavax.jws、javax.jws.soap、またはjavax.xml.wsパッケージにあります。例:

import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;
import javax.xml.ws.BindingType;

2

必要に応じて、追加のアノテーションをインポートします。

サポートされているJWSアノテーションの完全なリストについては、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスのアノテーション・サポートに関する項を参照してください。

3

必須の標準@WebService JWSアノテーションをクラス・レベルで追加して、JavaクラスがWebサービスを公開することを指定します。

「JWSファイルがWebサービスを実装することの指定(@WebServiceアノテーション)」を参照してください。

4

標準の@SOAPBinding JWSアノテーションをクラス・レベルで追加して、WebサービスとSOAPメッセージ・プロトコルの間のマッピングを指定する(オプション)

特に、このアノテーションを使用して、Webサービスがドキュメント・リテラルか、ドキュメント・エンコードかなどを指定します。「WebサービスとSOAPメッセージ・プロトコルのマッピングの指定(@SOAPBindingアノテーション)」を参照してください。

このJWSアノテーションは必須ではありませんが、JWSファイルで明示的に指定し、クライアント・アプリケーションがWebサービスの呼出しに使用するSOAPバインディングのタイプを明確にすることをお薦めします。

5

クラス・レベルでJAX-WS @BindingType JWSアノテーションを追加し、Webサービス・エンドポイント実装クラスに使用するバインディング・タイプを指定します。(オプション)

「エンドポイントに使用するバインディングの指定(@BindingTypeアノテーション)」を参照してください。

6

パブリック操作として公開するJWSファイルの各メソッドで標準の@WebMethodアノテーションを追加する(オプション)

必要に応じて、標準の@Onewayアノテーションを使用し、その操作が入力パラメータだけを取り、値を返さないことを指定します。「JWSメソッドをパブリック操作として公開することの指定(@WebMethodおよび@OneWayアノテーション)」を参照してください。

7

@WebParamアノテーションを追加し、公開される操作の入力パラメータの名前をカスタマイズする(オプション)

「操作のパラメータとWSDL要素のマッピングのカスタマイズ(@WebParamアノテーション)」を参照してください。

8

@WebResultアノテーションを追加し、公開される操作の戻り値の名前と動作をカスタマイズする(オプション)

「操作の戻り値とWSDL要素のマッピングのカスタマイズ(@WebResultアノテーション)」を参照してください。

9

独自のビジネス・コードを追加します。

Webサービスが希望どおりに動作するように、独自のビジネス・コードをメソッドに追加します。

JWSファイルの例

次のサンプルJWSファイルでは、簡単なWebサービスの実装方法を示します。

package examples.webservices.simple;
// Import the standard JWS annotation interfaces
import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;
// Standard JWS annotation that specifies that the porType name of the Web
// Service is "SimplePortType", the service name is "SimpleService", and the
// targetNamespace used in the generated WSDL is "http://example.org"
@WebService(name="SimplePortType", serviceName="SimpleService",
targetNamespace="http://example.org")
// Standard JWS annotation that specifies the mapping of the service onto the
// SOAP message protocol.  In particular, it specifies that the SOAP messages
// are document-literal-wrapped.
@SOAPBinding(style=SOAPBinding.Style.DOCUMENT,
use=SOAPBinding.Use.LITERAL,
parameterStyle=SOAPBinding.ParameterStyle.WRAPPED)
/**
* This JWS file forms the basis of simple Java-class implemented WebLogic
* Web Service with a single operation: sayHello
*
*/
public class SimpleImpl {
// Standard JWS annotation that specifies that the method should be exposed
// as a public operation.  Because the annotation does not include the
// member-value "operationName", the public name of the operation is the
// same as the method name: sayHello.
@WebMethod()
public String sayHello(String message) {
System.out.println("sayHello:" + message);
return "Here is the message: '" + message + "'";
}
}

JWSファイルがWebサービスを実装することの指定(@WebServiceアノテーション)

次のコードの抜粋のように、標準の@WebServiceアノテーションを使用して、JWSファイルがWebサービスを実装することをクラス・レベルで指定します。

@WebService(name="SimplePortType", serviceName="SimpleService",
targetNamespace="http://example.org")

この例では、Webサービスの名前はSimplePortTypeであり、jwsc Antタスクによって生成されるWSDLファイルのwsdl:portType要素に後でマップされます。サービス名はSimpleServiceであり、生成されるWSDLファイルのwsdl:service要素にマップされます。生成されるWSDLで使用されるターゲット・ネームスペースはhttp://example.orgです。

@WebServiceアノテーションの以下の追加の属性を指定することもできます。

- endpointInterface - 既存のサービス・エンドポイント・インタフェース・ファイルの完全修飾名。このアノテーションによって、実装からインタフェース定義を切り離すことができます。この属性を指定した場合、jwsc Antタスクはそのインタフェースを生成しません。そのインタフェースは作成されていて、CLASSPATHに入っていると想定します。

- portname - wsdl:port内で使用される名前。

@WebServiceアノテーションの属性はいずれも必須ではありません。各属性のデフォルト値については、Web Services Metadata for the Java Platform (JSR 181)仕様(http://www.jcp.org/en/jsr/detail?id=181)を参照してください。

WebサービスとSOAPメッセージ・プロトコルのマッピングの指定(@SOAPBindingアノテーション)

ここでは、WebサービスをSOAPメッセージ・プロトコルで使用できるようにします。そのためには、JWSファイル内にクラス・レベルで標準の@SOAPBindingアノテーションを含めて、WebサービスのSOAPバインディング(document-encodedまたはdocument-literal-wrappedなど)を指定します(次のコードの抜粋を参照)。

@SOAPBinding(style=SOAPBinding.Style.DOCUMENT,
use=SOAPBinding.Use.LITERAL,
parameterStyle=SOAPBinding.ParameterStyle.WRAPPED)

この例で、Webサービスはdocument-wrapped-styleエンコーディングとリテラル・メッセージ書式を使用しており、@SOAPBindingアノテーションを使用しない場合でも、これらはデフォルトの書式となります。一般に、最も相互運用性の高いタイプのWebサービスは、document-literal-wrappedのWebサービスです。

(style=SOAPBinding.Style.DOCUMENT属性と一緒に) parameterStyle属性を使用して、Webサービス操作のパラメータが、SOAPメッセージ本文全体を表すかどうか、操作と同じ名前の最上位要素内にラップされる要素かどうかを指定します。

次の表では、標準およびWebLogic固有の@SOAPBindingアノテーションの3つの属性の指定できる値とデフォルト値を示します。

表4-2 @SOAPBindingアノテーションの属性

属性

指定できる値

デフォルト値

style

SOAPBinding.Style.RPC

SOAPBinding.Style.DOCUMENT

SOAPBinding.Style.DOCUMENT

use

SOAPBinding.Use.LITERAL

SOAPBinding.Use.LITERAL

parameterStyle

SOAPBinding.ParameterStyle.BARE

SOAPBinding.ParameterStyle.WRAPPED

SOAPBinding.ParameterStyle.WRAPPED

JWSメソッドをパブリック操作として公開することの指定(@WebMethodおよび@OneWayアノテーション)

次のコードの抜粋で示すように、標準の@WebMethodアノテーションを使用して、JWSファイルのメソッドをWebサービスのパブリック操作として公開することを指定します。

public class SimpleImpl {
@WebMethod(operationName="sayHelloOperation")
public String sayHello(String message) {
System.out.println("sayHello:" + message);
return "Here is the message: '" + message + "'";
}
...

この例では、SimpleImpl JWSファイルのsayHello()メソッドが、Webサービスのパブリック操作として公開されます。ただし、operationName属性では、WSDLファイル内の操作のパブリック名はsayHelloOperationになることを指定しています。operationName属性を指定しない場合は、メソッドの名前が操作のパブリック名になります。

action属性を使用して操作のアクションを指定することもできます。SOAPをバインディングとして使用する場合、action属性の値によって、SOAPメッセージ内のSOAPActionヘッダーの値が決まります。

Webサービス操作としてメソッドを除外するには、@WebMethod(exclude="true")を指定します。

注意:
サービス・エンドポイント・インタフェース(SEI)は、JAX-WSのためにパブリック・メソッドを定義します。SEIが存在しない場合、@WebMethod(exclude="true")で明示的にタグ付けされていなければ、すべてのパブリック・メソッドがWebサービス操作として公開されます。

標準の@Onewayアノテーションを使用して、操作が呼出し側アプリケーションに値を返さないことを指定できます。次の例を参照してください。

public class OneWayImpl {
@WebMethod()
@Oneway()
public void ping() {
System.out.println("ping operation");
}
...

操作が一方向であることを指定する場合、実装するメソッドはvoidを返す必要があります。パラメータとしてホルダー・クラスを使用したり、チェック済み例外をスローしたりすることはできません。

@WebMethodアノテーションの属性はいずれも必須ではありません。@WebMethodおよび@Onewayアノテーションに関する追加情報や、各属性のデフォルト値については、Web Services Metadata for the Java Platform (JSR 181)仕様(http://www.jcp.org/en/jsr/detail?id=181)を参照してください。

操作のパラメータとWSDL要素のマッピングのカスタマイズ(@WebParamアノテーション)

次のコードの抜粋で示すように、標準の@WebParamアノテーションを使用して、Webサービス操作の入力パラメータと生成されるWSDLファイルの要素間のマッピングのカスタマイズや、パラメータ動作の指定を行います。

public class SimpleImpl {
@WebMethod()
@WebResult(name="IntegerOutput",
targetNamespace="http://example.org/docLiteralBare")
public int echoInt(
@WebParam(name="IntegerInput",
targetNamespace="http://example.org/docLiteralBare")
int input)
{
System.out.println("echoInt '" + input + "' to you too!");
return input;
}
...

この例では、生成されるWSDLファイル内のechoInt操作のパラメータ名はIntegerInputになります。JWSファイルに@WebParamアノテーションがない場合、生成されるWSDLファイル内のパラメータ名は、メソッドのパラメータ名inputと同じになります。targetNamespace属性は、パラメータのXMLネームスペースがhttp://example.org/docLiteralBareであることを指定します。この属性は、パラメータとXML要素がマップされる、ドキュメント・スタイルのSOAPバインディングを使用する場合にのみ有効です。

@WebParamアノテーションの以下の追加の属性を指定することもできます。

- mode - パラメータの入出力の方向(WebParam.Mode.IN、WebParam.Mode.OUT、またはWebParam.Mode.INOUT)。OUTおよびINOUTモードは、RPC形式の操作、またはヘッダーにマップされるパラメータでのみサポートされます。

- header - trueに設定した場合、パラメータの値はデフォルトの本文からではなくSOAPヘッダーから取得されることを指定する、ブール型の属性。

@WebParamアノテーションの属性はいずれも必須ではありません。各属性のデフォルト値については、Web Services Metadata for the Java Platform (JSR 181)仕様(http://www.jcp.org/en/jsr/detail?id=181)を参照してください。

操作の戻り値とWSDL要素のマッピングのカスタマイズ(@WebResultアノテーション)

次のコードの抜粋で示すように、標準の@WebResultアノテーションを使用して、Webサービス操作の戻り値と生成されるWSDLファイル内の対応する要素との間のマッピングをカスタマイズします。

public class Simple {
@WebMethod()
@WebResult(name="IntegerOutput",
targetNamespace="http://example.org/docLiteralBare")
public int echoInt(
@WebParam(name="IntegerInput",
targetNamespace="http://example.org/docLiteralBare")
int input)
{
System.out.println("echoInt '" + input + "' to you too!");
return input;
}
...

この例では、生成されるWSDLファイル内のechoInt操作の戻り値の名前はIntegerOutputになります。JWSファイルに@WebResultアノテーションがない場合、生成されるWSDLファイル内の戻り値の名前は、ハード・コード化された名前returnになります。targetNamespace属性は、戻り値のXMLネームスペースがhttp://example.org/docLiteralBareであることを指定します。この属性は、戻り値とXML要素がマップされる、ドキュメント・スタイルのSOAPバインディングを使用する場合にのみ有効です。

@WebResultアノテーションの属性はいずれも必須ではありません。各属性のデフォルト値については、Web Services Metadata for the Java Platform (JSR 181)仕様(http://www.jcp.org/en/jsr/detail?id=181)を参照してください。

エンドポイントに使用するバインディングの指定(@BindingTypeアノテーション)

JAX-WS javax.xml.ws.BindingTypeアノテーションを使用すると、Webサービス・エンドポイント実装クラスに使用するバインディングをカスタマイズできます。次のコードの抜粋を参照してください。

import javax.xml.ws.BindingType;
import javax.xml.ws.soap.SOAPBinding;
public class Simple {
@WebService()
@BindingType(value=SOAPBinding.SOAP12HTTP_BINDING)
public int echoInt(
@WebParam(name="IntegerInput",
targetNamespace="http://example.org/docLiteralBare")
int input)
{
System.out.println("echoInt '" + input + "' to you too!");
return input;
}
...

この例のデプロイされたエンド・ポイントでは、SOAP 1.2 over HTTPバインディングが使用されます。何も指定しない場合、バインディングのデフォルトはSOAP 1.1 over HTTPになります。

表4-3に、JAX-WS Webサービスでサポートされるバインディングを示します。

表4-3 JAX-WS Webサービスでサポートされるバインディング

バインディング

説明

javax.xml.ws.soap.SOAPBinding.SOAP12HTTP_BINDING

SOAP 1.2 over HTTPバインディング。

javax.xml.ws.soap.SOAPBinding.SOAP11HTTP_BINDING

SOAP 1.1 over HTTPバインディング。これがSOAP over HTTPトランスポート接続プロトコルのデフォルトです。

javax.xml.ws.soap.SOAPBinding.SOAP12HTTP_MTOM_BINDING

SOAP 1.2 over HTTPおよびMessage Transmission Optimized Mechanism (MTOM)バインディング

javax.xml.ws.soap.SOAPBinding.SOAP11HTTP_MTOM_BINDING

SOAP 1.1 over HTTPおよびMessage Transmission Optimized Mechanism (MTOM)バインディング

@BindingTypeアノテーションの以下の追加属性を指定することもできます。

- features - 指定したバインディングにおいて有効化/無効化する機能の配列。指定しない場合、機能は独自規則に基づいて有効化されます。

@BindingTypeアノテーションの詳細は、JAX-WS 2.1アノテーション(http://jax-ws.java.net/nonav/2.1.4/docs/annotations.html)を参照してください。

Webサービスの実行時情報へのアクセス

クライアント・アプリケーションが、JWSファイルで実装されたWebLogic Webサービスを呼び出すと、WebLogic Serverは、Webサービスやクライアントが、サービスに関する実行時情報のアクセス、および場合によっては変更に使用できるコンテキストを自動的に作成します。

実行時情報には、以下のいずれかの方法でアクセスできます。

- javax.xml.ws.BindingProvider (http://docs.oracle.com/javaee/6/api/javax/xml/ws/BindingProvider.html)- クライアント・アプリケーションから、プロトコル・バインディングのリクエストおよびレスポンス・コンテキストにアクセスします。「プロトコル・バインディング・コンテキストへのアクセス」を参照してください。

- javax.xml.ws.WebServiceContext (http://docs.oracle.com/javaee/6/api/javax/xml/ws/WebServiceContext.html)- Webサービスから、処理されているリクエストに関連する実行時メッセージ・コンテキストやセキュリティ情報にアクセスします。WebServiceContextは通常、@Resourceアノテーションを使用してエンドポイントにインジェクトされます。「Webサービス・コンテキストへのアクセス」を参照してください。

- javax.xml.ws.handler.MessageContext (http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/MessageContext.html)- WebサービスのWebServiceContextから直接、あるいはクライアント・アプリケーションやWebサービスのメッセージ・ハンドラから実行時プロパティ・セットにアクセスします。「MessageContextプロパティ値の使用」を参照してください。

以降の項では、BindingProvider、WebServiceContext、およびMessageContextを使用して実行時情報へアクセスする方法の詳細を説明します。

プロトコル・バインディング・コンテキストへのアクセス

注意:
com.sun.xml.ws.developer.JAXWSPropertiesおよびcom.sun.xml.ws.client.BindingProviderProperties APIは、JDK 6.0の拡張としてサポートされています。これらのAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

javax.xml.ws.BindingProviderインタフェースを使用すると、クライアント・アプリケーションから、プロトコル・バインディングのリクエストおよびレスポンス・コンテキストへアクセスすることができます。詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/ws/BindingProvider.htmlを参照してください。Webサービス・クライアント・ファイルの開発の詳細は、「Webサービス・クライアントの開発」を参照してください。

次に、コンテキストを使用してHTTPリクエスト・ヘッダー情報へアクセスする簡単なWebサービス・クライアント・アプリケーションの例を示します。太字のコードについては、例の後のプログラミングのガイドラインで説明しています。

package examples.webservices.hello_world.client;

import javax.xml.namespace.QName;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.Map;
import javax.xml.ws.BindingProvider;
import javax.xml.ws.handler.MessageContext;
import com.sun.xml.ws.developer.JAXWSProperties;
import com.sun.xml.ws.client.BindingProviderProperties;

/**
* This is a simple standalone client application that invokes the
* the <code>sayHelloWorld</code> operation of the Simple web service.
*/

public class Main {
public static void main(String[] args) {
HelloWorldService service;
try {
service = new HelloWorldService(new URL(args[0] + "?WSDL"),
new QName("http://hello_world.webservices.examples/",
"HelloWorldService") );
} catch (MalformedURLException murl) { throw new RuntimeException(murl); }
HelloWorldPortType port = service.getHelloWorldPortTypePort();
Map requestContext = ((BindingProvider)port).getRequestContext();
requestContext.put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://examples.com/HelloWorldImpl/HelloWorldService");
requestContext.put(JAXWSProperties.CONNECT_TIMEOUT, 300);
requestContext.put(BindingProviderProperties.REQUEST_TIMEOUT, 300);
String result = null;
result = port.sayHelloWorld("Hi there!");
System.out.println( "Got result: " + result );
Map responseContext = ((BindingProvider)port).getResponseContext();
Integer responseCode =
(Integer)responseContext.get(MessageContext.HTTP_RESPONSE_CODE);
...
}
}

この例の太字のコードで示すように、Webサービスの実行時コンテキストにアクセスするには、JWSファイルで次のガイドラインに従います。

- javax.xml.ws.BindingProvider APIに加え、使用する可能性のあるその他の関連APIをインポートします。

import java.util.Map;
import javax.xml.ws.BindingProvider;
import javax.xml.ws.handler.MessageContext;
import com.sun.xml.ws.developer.JAXWSProperties;
import com.sun.xml.ws.client.BindingProviderProperties;
import com.sun.xml.ws.client.BindingProviderProperties;

- BindingProviderクラスのメソッドを使用して、バインディング・プロトコル・コンテキスト情報へアクセスします。次の例は、プロトコル・バインディングのリクエストおよびレスポンス・コンテキストを取得してからリクエスト・コンテキスト用にクライアントで使用されるターゲットのサービス・エンドポイント・アドレスを設定し、リクエスト・コンテキストの接続や読取りのタイムアウト時間(ミリ秒単位)とHTTPレスポンス・ステータス・コードを設定する方法を示しています。

Map requestContext = ((BindingProvider)port).getRequestContext();
requestContext.put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://examples.com/HelloWorldImpl/HelloWorldService");
requestContext.put(JAXWSProperties.CONNECT_TIMEOUT, 300);
requestContext.put(BindingProviderProperties.REQUEST_TIMEOUT, 300);
../.
Map responseContext = ((BindingProvider)port).getResponseContext();
Integer responseCode =
(Integer)responseContext.get(MessageContext.HTTP_RESPONSE_CODE);

次の表は、Webサービスに関する実行時情報にアクセスするためにJWSファイルで使用できるjavax.xml.ws.BindingProviderのメソッドの要約を示します。

表4-4 BindingProviderのメソッド

メソッド

戻り値

説明

getBinding()

Binding

バインディング・プロバイダのバインディングを返します。

getRequestContext()

java.Util.Map

リクエスト・メッセージのコンテキストおよびメッセージの初期化に使用されるコンテキストを返します。

getResponseContext()

java.Util.Map

レスポンス・コンテキストを返します。

リクエストおよびレスポンス・コンテキストを取得したら、次の表で定義しているBindingProviderプロパティ値と、「MessageContextプロパティ値の使用」で定義しているMessageContextプロパティ値にアクセスできます。

表4-5 BindingProviderのプロパティ

プロパティ

タイプ

説明

ENDPOINT_ADDRESS_PROPERTY

java.lang.String

ターゲットのサービス・エンドポイント・アドレス。

PASSWORD_PROPERTY

java.lang.String

認証用パスワード。

SESSION_MAINTAIN_PROPERTY

java.lang.Boolean

サービス・クライアントがサービス・エンドポイントとのセッションに参加するかどうかを示すフラグ。デフォルト値のfalseは、サービス・クライアントが参加しないことを示します。

SOAPACTION_URI_PROPERTY

java.lang.String

SOAPAction URI.を指定するSOAPActionのプロパティ。このプロパティは、SOAPACTION_USE_PROPERTYがtrueに設定されている場合にのみ有効です。

SOAPACTION_USE_PROPERTY

java.lang.Boolean

SOAPActionを使用するかどうかを指定するSOAPActionのプロパティ。

USERNAME_PROPERTY

java.lang.String

認証用ユーザー名。

また、前の例の以下の点に注目してください。

- JAXWSProperties.CONNECT_TIMEOUTプロパティを使用して接続タイムアウトを定義しています。設定可能なJAXWSPropertiesの完全なリストは、com.sun.xml.ws.developer.JAXWSPropertiesのJavadoc (http://jax-ws.java.net/nonav/jax-ws-20-fcs/arch/com/sun/xml/ws/developer/JAXWSProperties.html#CONNECT_TIMEOUT)を参照してください。

- BindingProviderProperties.REQUEST_TIMEOUTプロパティを使用してリクエスト・タイムアウトを定義しています。設定可能なBindingProviderPropertiesの完全なリストは、com.sun.xml.ws.client.BindingProviderPropertiesのJavadoc (http://jax-ws.java.net/nonav/jax-ws-20-fcs/arch/com/sun/xml/ws/client/BindingProviderProperties.html#REQUEST_TIMEOUT)を参照してください。

Webサービス・コンテキストへのアクセス

javax.xml.ws.WebServiceContextインタフェースを使用すると、Webサービスから、処理されているリクエストに関連する実行時メッセージ・コンテキストやセキュリティ情報にアクセスできます。WebServiceContextは通常、@Resourceアノテーションを使用してエンドポイントにインジェクトされます。詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/ws/WebServiceContext.htmlを参照してください。

次に、コンテキストを使用してHTTPリクエスト・ヘッダー情報へアクセスする簡単なJWSファイルの例を示します。太字のコードについては、例の後のプログラミングのガイドラインで説明しています。

package examples.webservices.jws_context;
import javax.jws.WebMethod;
import javax.jws.WebService;
import java.util.Map;
import javax.xml.ws.WebServiceContext;
import javax.annotation.Resource;
import javax.xml.ws.handler.MessageContext;
@WebService(name="JwsContextPortType", serviceName="JwsContextService",
targetNamespace="http://example.org")
/**
* Simple web service to show how to use the @Context annotation.
*/
public class JwsContextImpl {
@Resource
private WebServiceContext ctx;
@WebMethod()
public String msgContext(String msg) {
MessageContext context=ctx.getMessageContext();
Map requestHeaders = (Map)context.get(MessageContext.HTTP_REQUEST_HEADERS);
}
}

この例の太字のコードで示すように、Webサービスの実行時コンテキストにアクセスするには、JWSファイルで次のガイドラインに従います。

- @javax.annotation.Resource JWSアノテーションをインポートします。

import javax.annotation.Resource;

- javax.xml.ws.WebServiceContext APIに加え、使用する可能性のあるその他の関連APIをインポートします。

import java.util.Map;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.handler.MessageContext;

- データ型javax.xml.ws.WebServiceContextのプライベート変数に、フィールド・レベルの@Resource JWSアノテーションを指定します。

@Resource
private WebServiceContext ctx;

- WebServiceContextクラスのメソッドを使用して、Webサービスの実行時情報にアクセスします。次の例は、現在のサービス・リクエストのメッセージ・コンテキストを取得してから、HTTPリクエスト・ヘッダーにアクセスする方法を示しています。

MessageContext context=ctx.getMessageContext();
Map requestHeaders = (Map)context.get(MessageContext.HTTP_REQUEST_HEADERS)

MessageContextプロパティ値の詳細は、「MessageContextプロパティ値の使用」を参照してください。

次の表は、Webサービスに関する実行時情報にアクセスするためにJWSファイルで使用できるjavax.xml.ws.WebServiceContextのメソッドの要約を示します。詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/ws/WebServiceContext.htmlを参照してください。

表4-6 WebServiceContextのメソッド

メソッド

戻り値

説明

getMessageContext()

MessageContext

現在のサービス・リクエストのMessageContextを返します。MessageContextプロパティ値の使用で定義しているように、HTTP_REQUEST_HEADERSやMESSAGE_ATTACHMENTSなど、アプリケーション・スコープのプロパティのみアクセス可能です。

getUserPrincipal()

java.security.Principal

現在のサービス・リクエストの送信者を識別するプリンシパルを返します。送信者が認証されていない場合、nullを返します。

isUserInRole(java.lang.String role)

boolean

指定された論理的なロールに認証ユーザーが含まれているかどうかを示すブール値を返します。ユーザーが認証されていない場合、falseを返します。

MessageContextプロパティ値の使用

次の表では、WebサービスのWebServiceContextから直接、あるいはクライアント・アプリケーションやWebサービスのメッセージ・ハンドラからアクセス可能なjavax.xml.ws.handler.MessageContextプロパティ値を示しています。詳細は、Javadocの「javax.xml.ws.handler.MessageContext」(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/MessageContext.html)を参照してください。

表4-7 MessageContextのプロパティ

プロパティ

タイプ

説明

HTTP_REQUEST_HEADERS

java.util.Map

リクエスト・メッセージのHTTPリクエスト・ヘッダーのマップ。

HTTP_REQUEST_METHOD

java.lang.String

GET、POST、PUTなどのHTTPリクエスト・メソッド。

HTTP_RESPONSE_CODE

java.lang.Integer

最終呼出しのHTTPレスポンス・ステータス・コード。

HTTP_RESPONSE_HEADERS

java.util.Map

HTTPレスポンス・ヘッダー。

INBOUND_MESSAGE_ATTACHMENTS

java.util.Map

インバウンド・メッセージの添付のマップ。

MESSAGE_OUTBOUND_PROPERTY

java.lang.Boolean

メッセージの方向。このプロパティは、アウトバウンド・メッセージの場合はtrue、インバウンド・メッセージの場合はfalseです。

OUTBOUND_MESSAGE_ATTACHMENTS

java.util.Map

アウトバウンド・メッセージの添付のマップ。

PATH_INFO

java.lang.String

リクエスト・パス情報。

QUERY_STRING

java.lang.String

リクエストの問合せ文字列。

REFERENCE_PARAMETERS

java.awt.List

WS-Addressing参照パラメータ。リストには、wsa:IsReferenceParameter="true"属性がマークされているすべてのSOAPヘッダーを含める必要があります。

SERVLET_CONTEXT

javax.servlet.ServletContext

リクエストに関連するサーブレット・コンテキスト・オブジェクト。

SERVLET_REQUEST

javax.servlet.http.HttpServletRequest

リクエストに関連するサーブレット・リクエスト・オブジェクト。

SERVLET_RESPONSE

javax.servlet.http.HttpServletResponse

リクエストに関連するサーブレット・レスポンス・オブジェクト。

WSDL_DESCRIPTION

org.xml.sax.InputSource

WSDLドキュメントの入力ソース(解決可能なURI)。

WSDL_INTERFACE

javax.xml.namespace.QName

ポート・タイプまたはWSDLインタフェースの名前。

WSDL_OPERATION

javax.xml.namespace.QName

現在のメッセージが所属するWSDL操作の名前。

WSDL_PORT

javax.xml.namespace.QName

メッセージを受け取ったWSDLポートの名前。

WSDL_SERVICE

javax.xml.namespace.QName

呼出し対象サービスの名前。

ステートレスまたはシングルトン・セッションEJBを実装すべき場合

jwsc Antタスクでは、JWSファイルを処理するときは常に、Webサービスの基底の実装としてプレーンJavaオブジェクトが選択されます。

しかし、Webサービスの基底の実装をステートレスまたはシングルトン・セッションEJBにして、EJBが提供するすべての機能(インスタンス・プール、トランザクション、セキュリティ、コンテナ管理による永続性、コンテナ管理による関係、データ・キャッシュなど)を活用することが必要な場合もあります。Webサービスの実装をEJBにする場合は、次の項のプログラミング・ガイドラインに従ってください。

EJB 3.0では、EJBを実装する場合に必要なEJBリモートおよびホーム・インタフェース・クラスおよびデプロイメント記述子ファイルを、手動で作成するのではなく、自動的に生成することができるメタデータ・アノテーションが導入されました。EJB 3.0の詳細は、『Oracle WebLogic Server Enterprise JavaBeansの開発』を参照してください。

デフォルトでは、EJBベースのWebサービスがJARファイルとしてパッケージ化されています。EJBベースのWebサービスを構築する場合、build.xmlファイルのjwsc Antタスクを更新して、module子要素のejbWsInWar属性を有効にすることにより、そのWebサービスがWARファイルとしてパッケージ化されるように指定できます。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』の「jwsc」を参照してください。

JWSファイルにEJBを実装するには、次の手順に従います。

- EJBアノテーションをインポートします。これらのアノテーションはすべてjavax.ejbパッケージにあります。少なくとも、@Statelessまたは@Singletonアノテーションはインポートする必要があります。JWSファイルに追加のEJBアノテーションを指定して、EJBの形状と動作を指定することもできます。詳細は、Javadocの「javax.ejb」(http://docs.oracle.com/javaee/6/api/javax/ejb/package-summary.html)を参照してください。
例:

import javax.ejb.Stateless;

- 少なくとも、クラス・レベルで@Statelessまたは@Singletonアノテーションを使用し、EJBを識別します。

@Stateless
public class SimpleEjbImpl {

以下の例では、ステートレス・セッションEJBを実装する簡単なJWSファイルを示します。関連するコードは太字で示されています。

package examples.webservices.jaxws;

import weblogic.transaction.TransactionHelper;
import javax.ejb.Stateless;
import javax.ejb.SessionContext;
import javax.ejb.TransactionAttribute;
import javax.ejb.TransactionAttributeType;
import javax.annotation.Resource;
import javax.jws.WebService;
import javax.jws.WebMethod;
import javax.transaction.SystemException;
import javax.transaction.Status;
import javax.transaction.Transaction;
import javax.xml.ws.WebServiceContext;

/**
* A transaction-awared stateless EJB-implemented JWS
*/

// Standard JWS annotation that specifies that the portName,serviceName and
// target Namespace of the Web Service.
@WebService(
name = "Simple",
portName = "SimpleEJBPort",
serviceName = "SimpleEjbService",
targetNamespace = "http://wls/samples")

//Standard EJB annotation
@Stateless
public class SimpleEjbImpl {

@Resource
private WebServiceContext context;
private String constructed = null;

// The WebMethod annotation exposes the subsequent method as a public
// operation on the Web Service.
@WebMethod()
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public String sayHello(String s) throws SystemException {
Transaction transaction =
TransactionHelper.getTransactionHelper().getTransaction();
int status = transaction.getStatus();
if (Status.STATUS_ACTIVE != status)
throw new IllegalStateException("transaction did not start,
status is: " + status + ", check ejb annotation processing");

return constructed + ":" + s;
}

ユーザー定義のJavaデータ型のプログラミング

Webサービス操作として公開されるJWSファイルのメソッドでは、パラメータや戻り値として必ずしも組込みのデータ型(Stringやintegerなど)を使用する必要はなく、独自に作成するJavaデータ型を使用することができます。ユーザー定義のデータ型の例としては、Stringの銘柄記号とintegerの売買株式数という2つのフィールドを持つTradeResultがあります。

JWSファイルで、1つまたは複数のメソッドのパラメータまたは戻り値としてユーザー定義のデータ型を使用する場合は、データ型のJavaコードを独自に作成して、JWSファイルにそのクラスをインポートし、適切に使用する必要があります。必要なデータ・バインディング・アーティファクトはすべて、jwsc Antタスクが後で作成します。

ユーザー定義のデータ型のJavaコードを記述するときは、以下の基本的な要件に従います。

- デフォルト・コンストラクタを定義します。これは、パラメータを取らないコンストラクタです。

- 公開するメンバー変数ごとにgetXXX()メソッドとsetXXX()メソッドの両方を定義します。

- 公開される各メンバー変数のデータ型は、組込みデータ型のいずれか、または組込みデータ型で構成されるユーザー定義のデータ型にします。

注意:
カスタム・マッピングを提供するにはJAXBを使用することができます。詳細は、「JAXBアノテーションを使用したJava-to-XMLスキーマ・マッピングのカスタマイズ」を参照してください。

jwsc Antタスクでは、最も一般的なXMLおよびJavaデータ型のデータ・バインディング・アーティファクトを生成できます。サポートされるユーザー定義のデータ型のリストは、「サポートされるユーザー定義のデータ型」を参照してください。サポートされる組込みデータ型の完全なリストは、「サポートされる組込みデータ型」参照してください。

次の例では、BasicStructという簡単なユーザー定義のJavaデータ型を示します。

package examples.webservices.complex;
/**
* Defines a simple JavaBean called BasicStruct that has integer, String,
* and String[] properties
*/
public class BasicStruct {
// Properties
private int intValue;
private String stringValue;
private String[] stringArray;
// Getter and setter methods
public int getIntValue() {
return intValue;
}
public void setIntValue(int intValue) {
this.intValue = intValue;
}
public String getStringValue() {
return stringValue;
}
public void setStringValue(String stringValue) {
this.stringValue = stringValue;
}
public String[] getStringArray() {
return stringArray;
}
public void setStringArray(String[] stringArray) {
this.stringArray = stringArray;
}
}

以下のJWSファイルの抜粋では、BasicStructクラスをインポートして、1つのメソッドのパラメータおよび戻り値として使用する方法を示しています。完全なJWSファイルについては、「サンプルComplexImpl.java JWSファイル」を参照してください。

package examples.webservices.complex;
// Import the standard JWS annotation interfaces
import javax.jws.WebMethod;
import javax.jws.WebParam;
import javax.jws.WebResult;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;
// Import the WebLogic-specific JWS annotation interface
// Import the BasicStruct JavaBean
import examples.webservices.complex.BasicStruct;
@WebService(serviceName="ComplexService", name="ComplexPortType",
targetNamespace="http://example.org")
...
public class ComplexImpl {
@WebMethod(operationName="echoComplexType")
public BasicStruct echoStruct(BasicStruct struct)
{
return struct;
}
}

JWSファイルからの別のWebサービスの呼出し

JWSファイル内から別のWebサービス(WebLogic ServerにデプロイされているWebサービス、または.NETなどの他のアプリケーション・サーバーにデプロイされているWebサービス)を呼び出すことができます。その手順は、「WebLogic WebサービスからのWebサービスの呼出し」で説明した手順と似ていますが、この場合は、clientgen Antタスクを実行してクライアント・スタブを生成するのではなく、呼出し側のWebサービスを構築するjwsc Antタスクに<clientgen>子要素を含めてクライアント・スタブを生成します。その後は、Java SEクライアント・アプリケーションの場合と同じように、JWSファイル内で標準のJAX-WS APIを使用します。

詳細な手順については、「別のWebLogic WebサービスからのWebサービスの呼出し」を参照してください。

SOAP 1.2の使用

WebLogic Webサービスでは、Webサービスとそのクライアントの間でデータや呼出しを転送する際に、メッセージ・フォーマットとしてデフォルトでバージョン1.1のSOAP (Simple Object Access Protocol)が使用されます。WebLogic Webサービスでは、SOAP 1.1と新しいSOAP 1.2の両バージョンがサポートされており、どちらのバージョンでも使用できます。

Webサービスでバージョン1.2のSOAPを使用することを指定するには、JWSファイルでクラス・レベルの@javax.xml.ws.BindingTypアノテーションを使用し、次の例に示すようにその唯一の属性の値をSOAPBinding.SOAP12HTTP_BINDINGに設定します(該当部分は太字で示してあります)。

package examples.webservices.soap12;
import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.xml.ws.BindingType;
import javax.xml.ws.SOAPBinding;
@WebService(name="SOAP12PortType",
serviceName="SOAP12Service",
targetNamespace="http://example.org")
@BindingType(value = SOAPBinding.SOAP12HTTP_BINDING)
/**
* This JWS file forms the basis of simple Java-class implemented WebLogic
* Web Service with a single operation: sayHello.  The class uses SOAP 1.2
* as its binding.
*
*/
public class SOAP12Impl {
@WebMethod()
public String sayHello(String message) {
System.out.println("sayHello:" + message);
return "Here is the message: '" + message + "'";
}
}

WebサービスでSOAP 1.2を使用する上で、Webサービスを呼び出すクライアント・アプリケーションを変更する場合も含め、このアノテーションを設定する以外の設定は必要ありません。WebLogic Webサービス・ランタイムによってすべて自動的に処理されます。

XMLスキーマの検証

デフォルトでは、SOAPメッセージはXMLスキーマに対して検証されません。後の項で説明するように、サーバーまたはクライアントでドキュメント・リテラルWebサービスに対してXMLスキーマ検証を有効化することができます。SOAPメッセージが無効の場合は、SOAPフォルトが返されます。

注意:
この機能により、Webサービス・リクエストに対してわずかな処理が追加されます。
デフォルトでは、SOAPフォルトの詳細にはスタック・トレースが含まれます。スタック・トレースを無効にするには、「SOAPフォルトからのスタック・トレースの無効化」を参照してください。

サーバーでのスキーマ検証の有効化

注意:
com.sun.xml.ws.developer.SchemaValidation APIは、JDK 6.0の拡張としてサポートされています。このAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

サーバーでスキーマ検証を有効化するには、エンドポイント実装で@SchemaValidationアノテーションを追加します。例:

import com.sun.xml.ws.developer.SchemaValidation;
import javax.jws.WebService;
@SchemaValidation
@WebService(name="HelloWorldPortType", serviceName="HelloWorldService")
public class HelloWorldImpl {
public String sayHelloWorld(String message) {
System.out.println("sayHelloWorld:" + message);
return "Here is the message: '" + message + "'";
}
}

アプリケーション内のエラーを管理する場合、独自の検証エラー・ハンドラ・クラスを引数としてアノテーションに渡すことができます。例:

@SchemaValidation(handler=ErrorHandler.class)

クライアントでのスキーマ検証の有効化

注意:
com.sun.xml.ws.developer.SchemaValidation APIは、JDK 6.0の拡張としてサポートされています。このAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

クライアントでスキーマ検証を有効化するには、SchemaValidationFeatureオブジェクトを作成し、PortTypeスタブ実装の作成時に引数として渡します。

package examples.webservices.hello_world.client;
import com.sun.xml.ws.developer.SchemaValidationFeature;
import javax.xml.namespace.QName;
import java.net.MalformedURLException;
import java.net.URL;
public class Main {
public static void main(String[] args) {
HelloWorldService service;
try {
service = new HelloWorldService(new URL(args[0] + "?WSDL"),
new QName("http://example.org", "HelloWorldService") );
} catch (MalformedURLException murl) { throw new RuntimeException(murl); }
SchemaValidationFeature feature =
new SchemaValidationFeature();
HelloWorldPortType port = service.getHelloWorldPortTypePort(feature);
String result = null;
result = port.sayHelloWorld("Hi there!");
System.out.println( "Got result: " + result );
}
}

アプリケーション内のエラーを管理する場合、独自の検証エラー・ハンドラを引数としてSchemaValidationFeatureオブジェクトに渡すことができます。例:

SchemaValidationFeature feature =
new SchemaValidationFeature(MyErrorHandler.class);
HelloWorldPortType port = service.getHelloWorldPortTypePort(feature);

JWSプログラミングのベスト・プラクティス

以下のリストでは、JWSファイルをプログラミングする場合のベスト・プラクティスを示します。

- document-literal-bareのWebサービスを作成する場合は、@WebParam JWSアノテーションを使用して、特定のWebサービスのすべての操作のすべての入力パラメータに一意の名前を付けるようにします。document-literal-bareのWebサービスの性質上、@WebParamアノテーションを使用して入力パラメータの名前を明示的に指定しない場合、WebLogic Serverが入力パラメータの名前を作成するため、Webサービス内でパラメータの名前が重複するおそれがあります。

- 一般に、最も相互運用性の高いタイプのWebサービスは、document-literal-wrappedのWebサービスです。

- ハード・コード化された名前returnに常に依存するのではなく、@WebResult JWSアノテーションを使用して、操作の戻り値の名前を明示的に設定します。JWSファイルで@WebResultアノテーションを使用しない場合、returnが戻り値のデフォルト名になります。

5 JAXBデータ・バインディングの使用

この章では、WebLogic Server 12.1.3のJava Architecture for XML Binding (JAXB)データ・バインディングの使用方法について説明します。

この章では、以下のトピックについて説明します。

- JAXBを使用したデータ・バインディングの概要

- JAXBデータ・バインディング・アーティファクトの開発

- 標準データ型のマッピング

- JAXBアノテーションを使用したJava-to-XMLスキーマ・マッピングのカスタマイズ

- バインディング宣言を使用したXMLスキーマ-to-Javaマッピングのカスタマイズ

- Glassfish RI JAXBデータ・バインディングおよびJAXBプロバイダの使用

JAXBを使用したデータ・バインディングの概要

様々なシステム間でのデータ交換にはXMLが標準的に使用されているため、Webサービス・アプリケーションには、Javaアプリケーションから直接XML形式データへアクセスする手段が必要となります。具体的には、XMLコンテンツをJavaアプリケーションで読み取れる形式に変換する必要があります。データ・バインディングでは、XML表現とJava表現間のデータ変換を記述します。

JAX-WSでは、JAXB (http://jcp.org/en/jsr/detail?id=222を参照)を使用してあらゆるデータ・バインディング・タスクを管理します。具体的には、JAXBによりJavaメソッド・シグネチャとWSDLのメッセージおよび操作がバインドされるため、実行時の変換が自動的に処理される一方で、そのマッピングをカスタマイズすることができます。これにより、XMLに関する知識がそれほどなくても、XMLデータと処理関数を、Javaテクノロジに基づくアプリケーションに簡単に組み込むことができます。

次の図に、JAXBのデータ・バインディング・プロセスを示します。

図5-1 JAXBでのデータ・バインディング

この図に示すように、JAXBのデータ・バインディング・プロセスは、以下のタスクから構成されます。

- バインド: XMLスキーマをスキーマ派生のJAXB Javaクラス、または値クラスにバインドします。各クラスは、一連のJavaBeanスタイルのアクセス・メソッド(getおよびsetメソッド)を介してコンテンツへのアクセスを提供します。バインディングは、JAXBのスキーマ・コンパイラによって管理されます。

- アンマーシャリング - XMLドキュメントを変換し、Javaプログラムの要素やオブジェクトのツリーを作成します。このツリーは、そのドキュメントのコンテンツおよび構成を表し、独自のJavaコードでアクセスできます。コンテンツ・ツリーでは、複合型は値クラスへマップされます。属性の宣言や要素(単純型)は、値クラス内のプロパティまたはフィールドへマップされ、それらの値にアクセスするにはgetおよびsetメソッドを使用します。アンマーシャリングは、JAXBの「バインディング・フレームワーク」によって管理されます。

- マーシャリング - JavaオブジェクトをXMLコンテンツへ変換します。この場合、WSDL操作としてデプロイされているJavaメソッドによって、wsdl:typesセクション内のスキーマ・コンポーネントが特定されます。マーシャリングは、JAXBのバインディング・フレームワークによって管理されます。

JAXBバインディング言語を使用すると、カスタム・バインディング宣言を定義したり、JAXBアノテーションを指定してXMLとJava間のデータ変換を制御することができます。

WebLogic Serverには、2種類のデータ・バインディングおよびJAXBプロバイダが用意されています。

- EclipseLink MOXy (WebLogic Serverの本リリースにおけるデフォルト)は、JAXB実装に完全に準拠しています。EclipseLink MOXyにはJAXBの標準機能に加えて、外部メタデータ・ファイルを使用して参照先のJavaソースを変更せずにJAXBアノテーションに相当するものを構成する機能やXPathベースのマッピングなど、便利な拡張が用意されています。JAXB拡張機能は、サービス・エンドポイント・インタフェース(SEI)のアノテーションまたはSEIで使用されるいずれかの値タイプで使用できます。JAXBをスタンドアロン・モードで使用しているユーザーも同様にこれらの機能を利用できます。
EclipseLink MOXyでは次のような追加拡張機能が提供されます。

- JPAエンティティからXMLへのマッピングのための拡張機能

- 双方向のマッピング

- 仮想プロパティ

- メタデータからブートストラップし、メモリー内ドメイン・クラス(Dynamic MOXy)を生成する機能

Webサービスでは、サーバー側でJavaからWSDLを生成する場合にのみEclipseLink MOXy拡張機能を利用できます。この場合、SEIと値タイプでEclipseLinkの拡張機能を使用できます。これらの拡張機能およびEclipseLink MOXyの詳細は、The EclipseLink MOXy (JAXB) User's Guide(http://wiki.eclipse.org/EclipseLink/UserGuide/MOXy)を参照してください。

EclipseLink MOXyプロバイダを使用する場合、構成は必要ありません。

- デフォルトのGlassfish JAXB実装であるGlassfish RI JAXBは、以前のリリースのWebLogic Serverではデフォルトで提供されるJAXBでした。Glassfish RI JAXBの固有機能は、EclipseLink MOXyでは機能しません。機能させる場合は、サーバー・レベルまたはアプリケーション・レベルでGlassfish RI JAXBデータ・バインディングおよびJAXBプロバイダを有効にできます。詳細は、「Glassfish RI JAXBデータ・バインディングおよびJAXBプロバイダの使用」を参照してください。

次の項では、WebLogic ServerでJAXBデータ・バインディングを使用する方法、さらには必要に応じてGlassfish RI JAXBプロバイダを構成する方法について説明します。

- JAXBデータ・バインディング・アーティファクトの開発 - WebLogic ServerでJAXBデータ・バインディング・アーティファクトを開発する方法を説明します。

- 標準データ型のマッピング - サポートされる標準の組込みデータ型およびユーザー定義データ型について説明します。

- JAXBアノテーションを使用したJava-to-XMLスキーマ・マッピングのカスタマイズ - JWSファイルでJAXBアノテーションを使用してJava-to-XMLスキーマ・マッピングを制御およびカスタマイズする方法について説明します。

- バインディング宣言を使用したXMLスキーマ-to-Javaマッピングのカスタマイズ - 別のファイルや埋込みインラインで定義されているバインディング宣言を使用して、XMLスキーマ-to-Javaマッピングを制御およびカスタマイズする方法について説明します。

- Glassfish RI JAXBデータ・バインディングおよびJAXBプロバイダの使用 - デフォルトのEclipseLink MOXy JAXBプロバイダのかわりにGlassfish RI JAXBデータ・バインディングおよびJAXBプロバイダを構成する場合に、サーバー全体レベルおよびアプリケーション・レベルで必要な手順について説明します。

JAXBデータ・バインディング・アーティファクトの開発

WebLogic ServerでJAXBデータ・バインディング・アーティファクトを開発する手順は、Javaクラス・ファイルとWSDLのどちらから開始するかによって異なります。

- Javaからの開始: このプログラミング・モデルを使用する場合、Javaクラスを作成します。JAXBは実行時にJavaオブジェクトをマーシャリングしてXMLコンテンツを生成し、このXMLコンテンツがSOAPメッセージ内にパッケージ化され、Webサービスのリクエストまたはレスポンスとして送信されます。
Java-to-XMLマッピングを制御するため、「JAXBアノテーションを使用したJava-to-XMLスキーマ・マッピングのカスタマイズ」で説明しているように、JWSファイルにJAXBアノテーションを含めます。カスタマイズが不要な場合、「組込みデータ型のJava-to-XMLマッピング」および「サポートされるユーザー定義のJavaデータ型」で説明しているように、JAXBは標準の組込みデータ型およびユーザー定義データ型のマッピングを使用します。

このプログラミング・モデルの詳細は、「Javaから開始するWebLogic Webサービスの開発: 主な手順」を参照してください。

- WSDLからの開始: このプログラミング・モデルを使用する場合、XMLスキーマが存在し、JAXBはXMLドキュメントをアンマーシャリングしてJavaオブジェクトを生成します。
XML-to-Javaマッピングを制御するため、「バインディング宣言を使用したXMLスキーマ-to-Javaマッピングのカスタマイズ」で説明しているように、カスタム・バインディング宣言をWSDLまたはXMLスキーマ内で、あるいは外部ファイルで定義できます。カスタマイズが不要な場合、「組込みデータ型のXML-to-Javaマッピング」および「サポートされるユーザー定義のXMLデータ型」で説明しているように、標準の組込みデータ型およびユーザー定義データ型のマッピングが使用されます。

このプログラミング・モデルの詳細は、「WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順」を参照してください。

こららの手順で説明しているjwsc、wsdlc、またはclientgen Antタスクを呼び出す場合、以下の点に注意する必要があります。

- JAX-WS WebサービスおよびJAXBバインディング・アーティファクトを生成するには、type="JAXWS"属性を指定する必要があります。jwscでは、<jws>子要素の一部としてtype属性を指定します。

- 必要に応じて、<binding>子要素を指定し、JAX-WSおよびJAXBのデータ・バインディングのカスタマイズ情報を格納するカスタマイズ・ファイルを指定することができます。カスタマイズ・ファイルの作成に関する情報は「バインディング宣言を使用したXMLスキーマ-to-Javaマッピングのカスタマイズ」を参照してください。カスタマイズが不要な場合、「標準データ型のマッピング」で説明しているように、JAXBは標準の組込みデータ型およびユーザー定義データ型のマッピングを使用します。

jwsc、wsdlc、またはclientgen Antタスクの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のAntタスク・リファレンスに関する項を参照してください。

標準データ型のマッピング

WebLogic Webサービスでは、JSR 222: JavaTM Architecture for XML Binding (JAXB) 2.0仕様(http://jcp.org/en/jsr/detail?id=222)の規定に従って組込みのXMLスキーマ、Java、およびSOAPのデータ型がサポートされており、追加のプログラミング手順を踏まずに、そうしたデータ型をWebサービス操作で使用できます。組込みデータ型には、integer、string、timeなどがあります。

また、Webサービスの入力パラメータや戻り値として、様々なユーザー定義のXMLおよびJavaデータ型を使用できます。ユーザー定義のデータ型には、XMLスキーマやJavaの構成要素から作成する<xsd:complexType>やJavaBeanなどがあります。jwscやclientgenなどのWebLogic WebサービスAntタスクでは、ユーザー定義のデータ型をXML表現とJava表現の間で変換するのに必要なデータ・バインディング・アーティファクトが自動的に生成されます。XML表現はSOAPリクエストやレスポンス・メッセージで使用し、Java表現はWebサービスを実装するJWSで使用します。

以下の項では、JAXBでサポートされている組込みデータ型およびユーザー定義データ型について説明します。

- サポートされる組込みデータ型

- サポートされるユーザー定義のデータ型

サポートされる組込みデータ型

次の各項では、WebLogic Webサービスがサポートする組込みデータ型、およびそのXML表現とJava表現の間のマッピングについて説明します。Webサービスを実装するバックエンド・コンポーネントのパラメータと戻り値のデータ型が、組込みデータ型のセットの中にあるかぎり、データはWebLogic Serverによって、XMLとJava間で自動的に変換されます。

ユーザー定義のデータ型を使用する場合は、XMLとJava間でデータを変換するデータ・バインディング・アーティファクトを作成する必要があります。WebLogic Serverには、ほとんどのユーザー定義データ型のデータ・バインディング・アーティファクトを自動的に生成可能なjwscおよびwsdlc Antタスクが用意されています。サポートされるXMLとJavaのデータ型については、「サポートされるユーザー定義のデータ型」を参照してください。

組込みデータ型のXML-to-Javaマッピング

次の表に、サポートされるXMLスキーマ・データ型(ターゲット・ネームスペースhttp://www.w3.org/2001/XMLSchema)と、それぞれに対応するJavaデータ型をアルファベット順に示します。サポートされるユーザー定義のXMLデータ型については、「組込みデータ型のJava-to-XMLマッピング」を参照してください。

表5-1 XMLスキーマの組込みデータ型とJavaデータ型のマッピング

XMLスキーマ・データ型

Javaデータ型(小文字はプリミティブ・データ型を示します)

anySimpleType (この型のxsd:element用)

java.lang.Object

anySimpleType (この型のxsd:attribute用)

java.lang.String

base64Binary

byte[]

boolean

boolean

byte

byte

date

java.xml.datatype.XMLGregorianCalendar

dateTime

javax.xml.datatype.XMLGregorianCalendar

decimal

java.math.BigDecimal

double

double

duration

javax.xml.datatype.Duration

float

float

g

java.xml.datatype.XMLGregorianCalendar

hexBinary

byte[]

int

int

integer

java.math.BigInteger

long

long

NOTATION

javax.xml.namespace.QName

QName

javax.xml.namespace.QName

short

short

string

java.lang.String

time

java.xml.datatype.XMLGregorianCalendar

unsignedByte

short

unsignedInt

long

unsignedShort

int

次の例はJAXB仕様からの抜粋ですが、デフォルトのXML-to-Javaバインディングの例を示しています。

XMLスキーマ

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<xsd:element name="purchaseOrder" type="PurchaseOrderType"/>
<xsd:element name="comment" type="xsd:string"/>
<xsd:complexType name="PurchaseOrderType">
<xsd:sequence>
<xsd:element name="shipTo" type="USAddress"/>
<xsd:element name="billTo" type="USAddress"/>
<xsd:element ref="comment" minOccurs="0"/>
<xsd:element name="items" type="Items"/>
</xsd:sequence>
<xsd:attribute name="orderDate" type="xsd:date"/>
</xsd:complexType>
<xsd:complexType name="USAddress">
<xsd:sequence>
<xsd:element name="name" type="xsd:string"/>
<xsd:element name="street" type="xsd:string"/>
<xsd:element name="city" type="xsd:string"/>
<xsd:element name="state" type="xsd:string"/>
<xsd:element name="zip" type="xsd:decimal"/>
</xsd:sequence>
<xsd:attribute name="country" type="xsd:NMTOKEN" fixed="US"/>
</xsd:complexType>
<xsd:complexType name="Items">
<xsd:sequence>
<xsd:element name="item" minOccurs="1" maxOccurs="unbounded">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="productName" type="xsd:string"/>
<xsd:element name="quantity">
<xsd:simpleType>
<xsd:restriction base="xsd:positiveInteger">
<xsd:maxExclusive value="100"/>
</xsd:restriction>
</xsd:simpleType>
</xsd:element>
<xsd:element name="USPrice" type="xsd:decimal"/>
<xsd:element ref="comment" minOccurs="0"/>
<xsd:element name="shipDate" type="xsd:date"
minOccurs="0"/>
</xsd:sequence>
<xsd:attribute name="partNum" type="SKU" use="required"/>
</xsd:complexType>
</xsd:element>
</xsd:sequence>
</xsd:complexType>
<!-- Stock Keeping Unit, a code for identifying products -->
<xsd:simpleType name="SKU">
<xsd:restriction base="xsd:string">
<xsd:pattern value="\d{3}-[A-Z]{2}"/>
</xsd:restriction>
</xsd:simpleType>
</xsd:schema>

デフォルトJavaバインディング

import javax.xml.datatype.XMLGregorianCalendar; import java.util.List;
public class PurchaseOrderType {
USAddress getShipTo(){...}
void setShipTo(USAddress){...}
USAddress getBillTo(){...}
void setBillTo(USAddress){...}
/** Optional to set Comment property. */
String getComment(){...}
void setComment(String){...}
Items getItems(){...}
void setItems(Items){...}
XMLGregorianCalendar getOrderDate()
void setOrderDate(XMLGregorianCalendar)
};
public class USAddress {
String getName(){...}
void setName(String){...}
String getStreet(){...}
void setStreet(String){...}
String getCity(){...}
void setCity(String){...}
String getState(){...}
void setState(String){...}
int getZip(){...}
void setZip(int){...}
static final String COUNTRY="USA";
};
public class Items {
public class ItemType {
String getProductName(){...}
void setProductName(String){...}
/** Type constraint on Quantity setter value 0..99.*/
int getQuantity(){...}
void setQuantity(int){...}
float getUSPrice(){...}
void setUSPrice(float){...}
/** Optional to set Comment property. */
String getComment(){...}
void setComment(String){...}
XMLGregorianCalendar getShipDate();
void setShipDate(XMLGregorianCalendar);
/** Type constraint on PartNum setter value "\d{3}-[A-Z]{2}".*/
String getPartNum(){...} void setPartNum(String){...}
};
/** Local structural constraint 1 or more instances of Items.ItemType.*/
List<Items.ItemType> getItem(){...}
}
public class ObjectFactory {
// type factories
Object newInstance(Class javaInterface){...}
PurchaseOrderType createPurchaseOrderType(){...}
USAddress createUSAddress(){...}
Items createItems(){...}
Items.ItemType createItemsItemType(){...}
// element factories
JAXBElement<PurchaseOrderType>createPurchaseOrder(PurchaseOrderType){...}
JAXBElement<String> createComment(String value){...}
}

組込みデータ型のJava-to-XMLマッピング

次の表に、サポートされているJavaデータ型と、それぞれに対応するXMLスキーマ・データ型をアルファベット順に示します。サポートされるユーザー定義のJavaデータ型については、「サポートされるユーザー定義のJavaデータ型」を参照してください。

表5-2 Javaデータ型とXMLスキーマ・データ型のマッピング

Javaデータ型(小文字はプリミティブ・データ型を示します)

XMLスキーマ・データ型

boolean

boolean

byte

byte

double

double

float

float

long

long

int

int

javax.activation.DataHandler

base64Binary

java.awt.Image

base64Binary

java.lang.Object

anyType

java.lang.String

string

java.math.BigInteger

integer

java.math.BigDecimal

decimal

java.net.URI

string

java.util.Calendar

dateTime

java.util.Date

dateTime

java.util.UUID

string

javax.xml.datatype.XMLGregorianCalendar

anySimpleType

javax.xml.datatype.Duration

duration

javax.xml.namespace.QName

Qname

javax.xml.transform.Source

base64Binary

short

short

サポートされるユーザー定義のデータ型

以降の項の表には、jwscおよびwsdlc Antタスクでデータ・バインディング・アーティファクトを自動的に生成できるユーザー定義のXMLデータ型およびJavaデータ型(対応するJava表現またはXML表現など)をまとめます。

これらの表にないXMLデータ型またはJavaデータ型で、「サポートされる組込みデータ型」の表に示した組込みデータ型でもない型の場合は、ユーザー定義データ型のアーティファクトを手動で作成する必要があります。

サポートされるユーザー定義のXMLデータ型

次の表に、jwscおよびwsdlc AntタスクでサポートされるXMLスキーマ・データ型と、それぞれに対応するJavaデータ型またはマッピング・メカニズムをまとめます。

表5-3 サポートされているユーザー定義のXMLスキーマ・データ型

XMLスキーマ・データ型

同等のJavaデータ型またはマッピング・メカニズム

単純型および複合型の両方の要素を持つ<xsd:complexType>

JavaBean

単純なコンテンツを含む<xsd:complexType>

JavaBean

<xsd:complexType>の<xsd:attribute>

JavaBeanのプロパティ。

既存の単純型の制限による新しい単純型の派生

同等の単純型のJavaデータ型。

制限要素で使用されるファセット

シリアライゼーションおよびデシリアライゼーションで強制されないファセット。

<xsd:list>

リスト・データ型の配列。

wsdl:arrayType属性を使用した制限によってsoapenc:Arrayから派生する配列

arrayTypeデータ型と同等のJavaデータ型の配列。

制限によってsoapenc:Arrayから派生する配列

同等のJavaデータ型の配列。

単純型からの複合型の派生

_valueというプロパティのあるJavaBean。_valueの型は、この項の規則に従って単純型からマップされます。

<xsd:anyType>

java.lang.Object

<xsd:any>

java.lang.Object

<xsd:any[]>

java.lang.Object

<xsd:union>

ユニオン・メンバーの共通の親タイプ。

<xsi:nil>および<xsd:nillable>属性

Javaのnull値。

XMLデータ型が組込みデータ型で通常はJavaプリミティブ・データ型(intやshortなど)にマップされる場合、そのXMLデータ型は実際には同等のオブジェクト・ラッパー型(java.lang.Integerやjava.lang.Shortなど)にマップされます。

複合型の派生

Javaの継承を使用してマップされます。

抽象型

抽象Javaデータ型。

サポートされるユーザー定義のJavaデータ型

次の表は、jwscおよびwsdlc Antタスクでサポートされるユーザー定義のJavaデータ型と、それぞれに対応するXMLスキーマ・データ型の一覧です。

表5-4 サポートされるユーザー定義のJavaデータ型

Javaデータ型

同等のXMLスキーマ・データ型

サポートされている任意のデータ型をプロパティとするJavaBean

JavaBeanプロパティに対応する要素の<xsd:sequence>をコンテンツ・モデルとする<xsd:complexType>。

サポートされるすべてのデータ型の配列および多次元配列(JavaBeanプロパティとして使用する場合)

maxOccurs属性がunboundedに設定されている<xsd:complexType>内の要素。

java.lang.Object

注意: 実行時オブジェクトのデータ型は既知の型でなければなりません。

<xsd:anyType>

java.util.Collection

リテラル配列。

java.util.List

リテラル配列。

java.util.ArrayList

リテラル配列。

java.util.LinkedList

リテラル配列。

java.util.Vector

リテラル配列。

java.util.Stack

リテラル配列。

java.util.Set

リテラル配列。

java.util.TreeSet

リテラル配列。

java.utils.SortedSet

リテラル配列。

java.utils.HashSet

リテラル配列。

JAXBアノテーションを使用したJava-to-XMLスキーマ・マッピングのカスタマイズ

必要に応じて、JAXBアノテーションを使用してJava-to-XMLスキーマ・マッピングのデフォルト・バインディング規則をオーバーライドすることができます。表5-5に、JavaオブジェクトをXMLにマッピングする方法を制御するためにJWSファイルに含めることができるJAXBマッピング・アノテーションを示します。これらの各アノテーションは、javax.xml.bind.annotationパッケージ(http://docs.oracle.com/javaee/6/api/javax/xml/bind/annotation/package-summary.htmlを参照)で利用できます。

表5-5 JAXBマッピング・アノテーション

アノテーション

説明

@XmlAccessorType

デフォルトでフィールドやプロパティをマップするかどうかを指定します。フィールドおよびプロパティのデフォルト・シリアライゼーションの指定(@XmlAccessorTypeアノテーション)を参照してください。

@XmlElement

クラスに格納されているプロパティを、格納しているクラスがマップされているXMLスキーマの複合型のローカル要素へマップします。プロパティとローカル要素のマッピング(@XmlElement)を参照してください。

@XMLMimeType

image/jpegなど、プロパティのXML表現を制御するMIMEタイプとテキスト表現を関連付けます。MIMEタイプの指定(@XmlMimeTypeアノテーション)を参照してください。

@XmlRootElement

WebサービスのWSDLによって使用されるXMLスキーマのグローバル要素に最上位クラスをマップします。「最上位クラスとグローバル要素のマッピング(@XmlRootElement)」を参照してください。

@XmlSeeAlso

現在のクラスをバインディングする際に他のクラスをバインドします。複数のクラスのバインディング(@XmlSeeAlso)を参照してください。

@XmlType

XMLスキーマ型にクラスまたは列挙型をマップします。値クラスとスキーマ型のマッピング(@XmlType)を参照してください。

以下の項に、サポートされている組込みデータ型およびユーザー定義データ型のXMLスキーマに対するJavaオブジェクトのデフォルト・マッピングを示します。

- 組込みデータ型のJava-to-XMLマッピング

- サポートされるユーザー定義のJavaデータ型

JAXBアノテーションの例

次に、JAXBアノテーションの例を示します。

@XmlRootElement(name = "ComplexService", namespace ="http://examples.org")
@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "basicStruct", propOrder = {
"intValue",
"stringArray",
"stringValue"
)
public class BasicStruct {
protected int intValue;
@XmlElement(nillable = true)
protected List<String> stringArray;
protected String stringValue;
public int getIntValue() {
return intValue;
}
public void setIntValue(int value) {
this.intValue = value;
}
public List<String> getStringArray() {
if (stringArray == null) {
stringArray = new ArrayList<String>();
}
return this.stringArray;
}

public String getStringValue() {
return stringValue;
}
public void setStringValue(String value) {
this.stringValue = value;
}
}

フィールドおよびプロパティのデフォルト・シリアライゼーションの指定(@XmlAccessorTypeアノテーション)

@XmlAccessorTypeアノテーションは、フィールドやプロパティをデフォルトでマッピングするかどうかを指定します。このアノテーションは、次のJavaプログラム要素に対して指定できます。

- パッケージ

- 最上位クラス

@XmlAccessorTypeは、@XmlType (値クラスとスキーマ型のマッピング(@XmlType))および@XmlRootElement (最上位クラスとグローバル要素のマッピング(@XmlRootElement))アノテーションで指定されます。

次の表に、@XmlAccessorTypeアノテーションに渡すことができる省略可能な要素を示します。

表5-6 @XMLAccessorTypeアノテーションの省略可能な要素

要素

説明

value

XMLAccessType.valuevalueを指定します。valueは以下のいずれかの値です。

- FIELD - フィールドがXMLにバインドされます。

- PROPERTY - JavaBeanプロパティおよびアノテーション付きのフィールドがXMLにバインドされます。

- PUBLIC_MEMBER - パブリック・フィールド、アノテーション付きのフィールド、およびJavaBeanプロパティがXMLにバインドされます。これがデフォルトです。

- NONE - アノテーション付きのフィールドとプロパティのみがXMLにバインドされます。

詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/bind/annotation/XmlAccessorType.htmlにあるJavadocの「javax.xml.bind.annotation.XmlAccessorType」を参照してください。例については、JAXBアノテーションの例の項を参照してください。

プロパティとローカル要素のマッピング(@XmlElement)

@XmlElementアノテーションは、クラスに格納されているプロパティを、格納しているクラスがマップされているXMLスキーマの複合型のローカル要素へマップします。このアノテーションは、次のJavaプログラム要素に対して指定できます。

- JavaBeanプロパティ

- 非静的な永続フィールド

次の表に、@XmlElementアノテーションに渡すことができるアノテーション要素を示します。

表5-7 @XMLElementアノテーションの省略可能な要素

要素

説明

name

JavaBeanのプロパティを表すXML要素のローカル名。この要素のデフォルトは、JavaBeanプロパティ名。

namespace

JavaBeanのプロパティを表すXML要素のネームスペース。デフォルトのネームスペースは、格納しているクラスのネームスペースから派生します。

nillable

nullを許容するように要素宣言をカスタマイズします。

詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/bind/annotation/XmlElement.htmlにあるJavadocの「javax.xml.bind.annotation.XmlElement」を参照してください。

MIMEタイプの指定(@XmlMimeTypeアノテーション)

@XmlMimeTypeアノテーションは、プロパティのXML表現を制御するMIMEタイプを指定します。このアノテーションは、XMLのxsd:base64BinaryバイナリにバインドされるImageやSourceなどのデータ型に対して指定できます。

次の表に、@XmlMimeTypeアノテーションに渡すことができる必須の要素を示します。

表5-8 @XMLMimeTypeアノテーションの必須要素

要素

説明

value

image/jpegやtext/xmlなど、MIMEタイプのテキスト表現を指定します。

詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/bind/annotation/XmlMimeType.htmlにあるJavadocの「javax.xml.bind.annotation.XmlMimeType」を参照してください。

最上位クラスとグローバル要素のマッピング(@XmlRootElement)

@XmlRootElementアノテーションは、WebサービスのWSDLによって使用されるXMLスキーマのグローバル要素に最上位クラスをマップします。このアノテーションは、次のJavaプログラム要素に対して指定できます。

- 最上位クラス

- 列挙型

@XmlRootElementは、@XmlType (値クラスとスキーマ型のマッピング(@XmlType))および@XmlAccessorType(フィールドおよびプロパティのデフォルト・シリアライゼーションの指定(@XmlAccessorType Annotation))アノテーションで指定されます。

次の表に、@XmlRootElementアノテーションに渡すことができる省略可能な要素を示します。

表5-9 @XmlRootElementアノテーションの省略可能な要素

要素

説明

name

XML要素のローカル名。この要素のデフォルトはクラス名です。

namespace

XML要素のネームスペース。デフォルトのネームスペースは、クラスのパッケージから派生します。

詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/bind/annotation/XmlRootElement.htmlにあるJavadocの「javax.xml.bind.annotation.XmlRootElement」を参照してください。例については、JAXBアノテーションの例の項を参照してください。

複数のクラスのバインディング(@XmlSeeAlso)

@XmlSeeAlsoアノテーションは、現在のクラスをバインドする際にクラスのリストをバインドします。次の表に、@XMLRootElementアノテーションに渡すことができる省略可能な要素を示します。

表5-10 @XmlSeeAlsoアノテーションの省略可能な要素

要素

説明

value

現在のクラスをバインドする際にJAXBで使用されるクラスのリスト。

値クラスとスキーマ型のマッピング(@XmlType)

@XmlTypeアノテーションは、クラスまたは列挙型をXMLスキーマ型にマップします。型は単純型または複合型の場合があります。このアノテーションは、次のJavaプログラム要素に対して指定できます。

- 最上位クラス

- 列挙型

@XmlTypeは、@XmlRootElement (最上位クラスとグローバル要素のマッピング(@XmlRootElement))および@XmlAccessorType (フィールドおよびプロパティのデフォルト・シリアライゼーションの指定(@XmlAccessorType Annotation))アノテーションで指定されます。

次の表に、@XmlTypeアノテーションに渡すことができる省略可能な要素を示します。

表5-11 @XmlTypeアノテーションの省略可能な要素

要素

説明

name

クラスのマップ先のXMLスキーマ型の名前。

namespace

XMLスキーマ型のターゲット・ネームスペースの名前。デフォルトは、クラスを格納しているパッケージがマップされるターゲット・ネームスペース。

propOrder

クラスで定義されているJavaBeanプロパティ名のリスト。このリストは、クラスがXMLスキーマの複合型へマップされる際のXMLスキーマ要素の順番を定義します。リスト内の各名前は、JavaBeanプロパティのJava識別子の名前です。すべてのJavaBeanプロパティをリストする必要があります。

詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/bind/annotation/XmlType.htmlにあるJavadocの「javax.xml.bind.annotation.XmlType」を参照してください。例については、JAXBアノテーションの例の項を参照してください。

バインディング宣言を使用したXMLスキーマ-to-Javaマッピングのカスタマイズ

WSDLファイルの分散的特性から、現在のアプリケーションの要件を満たすためにその中身を常に制御または変更できるとは限りません。たとえば、WSDLファイルを所有していなかったり、パートナがすでに使用している場合は、変更を加えるのは非現実的または不可能です。

WSDLファイルを直接編集できない場合、カスタム・バインディング宣言を指定することによって、WSDLコンポーネントがJavaオブジェクトへマップされる方法をカスタマイズすることができます。バインディング宣言を使用すると、非同期性、ラッパー形式など、特定の機能を制御したり、XMLスキーマのカスタマイズにより生成されるJAXBデータ・バインディング・アーティファクトを制御することもできます。

バインディング宣言は以下のいずれかの方法で定義することができます。

- 特定のWSDLまたはXMLスキーマ・ドキュメントのすべてのバインディング宣言を格納する外部のバインディング宣言ファイルを作成します。「外部バインディング宣言ファイルの作成」を参照してください。

注意:
カスタマイズが必要な場合、WSDLまたはXMLスキーマ・ドキュメントからカスタマイズを分離し、この方法で柔軟性を保つことをお薦めします。

- WSDLまたはXMLスキーマ・ドキュメント内にバインディング宣言を埋め込みます。「バインディング宣言の埋め込み」を参照してください。

選択する方法に関係なく、どのバインディング宣言も意味的には同じです。

カスタム・バインディング宣言は、次の図に示すようにスコープに関連付けられます。

図5-2 カスタム・バインディング宣言のスコープ

次の表で、各スコープの意味を説明します。

図5-12 カスタム・バインディング宣言のスコープ

スコープ

定義

グローバル・スコープ

グローバル・スコープのカスタマイズ値を表します。具体的には、次のとおりです。

- JAX-WSバインディング宣言の場合、ルート要素の一部として定義されるカスタマイズ値を表します。「ルート要素の指定」を参照してください。

- JAXBアノテーションの場合、<globalBindings>バインディング宣言内に格納されるカスタマイズ値を表します。グローバル・スコープの値は、ソース・スキーマのすべてのスキーマ要素の他に、含まれる、またはインポートされるあらゆるスキーマに適用されます。

スキーマ・スコープ

<schemaBindings>バインディング宣言内に格納されるJAXBカスタマイズ値を表します。スキーマ・スコープの値は、スキーマのターゲット・ネームスペース内の要素に適用されます。

注意: このスコープが適用されるのはJAXBバインディング宣言のみです。

定義スコープ

グローバル宣言または型定義のバインディング宣言で定義されるJAXBカスタマイズ値を表します。定義スコープの値は、グローバル宣言または型定義を参照する要素に適用されます。

注意: このスコープが適用されるのはJAXBバインディング宣言のみです。

コンポーネント・スコープ

アノテーションが付けられたスキーマ要素またはWSDLに適用されるカスタマイズ値を表します。

カスタム・バインディング宣言のスコープは、以下の継承およびオーバーライド規則に準拠します。

- 継承 - カスタマイズ値は上から下へ継承されます。たとえば、コンポーネント・スコープのWSDL要素(JAX-WS)は、グローバル・スコープで定義されているカスタマイズ値を継承します。コンポーネント・スコープのスキーマ要素(JAXB)は、グローバル・スコープ、スキーマ・スコープ、および定義スコープで定義されているカスタマイズ値を継承します。

- オーバーライド - カスタマイズ値は下から上へオーバーライドされます。たとえば、コンポーネント・スコープのWSDL要素(JAX-WS)は、グローバル・スコープで定義されているカスタマイズ値をオーバーライドします。コンポーネント・スコープのスキーマ要素(JAXB)は、定義スコープ、スキーマ・スコープ、およびグローバル・スコープで定義されているカスタマイズ値をオーバーライドします。

以下の項では、カスタム・バインディング宣言の作成方法と、標準のカスタム・バインディング宣言について説明します。

- 外部バインディング宣言ファイルの作成

- バインディング宣言の埋め込み

- JAX-WSカスタム・バインディング宣言

- JAXBカスタム・バインディング宣言

カスタム・バインディング宣言の使用に関する詳細は、以下を参照してください。

- JAX-WS WSDLのカスタマイズ(http://jax-ws.java.net/nonav/2.1.2/docs/customizations.html)

- JAXB仕様(http://jcp.org/en/jsr/detail?id=222)の「Customizing XML Schema to Java Representation Binding」

外部バインディング宣言ファイルの作成

特定のWSDLまたはXMLスキーマ・ドキュメントのすべてのバインディング宣言を格納する外部のバインディング宣言ファイルを作成します。次に、バインディング宣言ファイルをwsdlc、jwsc、またはclientgen Antタスクの<binding>子要素に渡します。

以降の項で説明する内容は、次のとおりです。

- JAX-WSバインディング宣言を使用した外部バインディング宣言ファイルの作成

- JAXBバインディング宣言を使用した外部バインディング宣言ファイルの作成

JAX-WSバインディング宣言を使用した外部バインディング宣言ファイルの作成

以下の項では、JAX-WSバインディング宣言ファイルのルート要素および子要素の指定方法について説明します。定義可能なカスタム・バインディング宣言については、「JAX-WSカスタム・バインディング宣言」を参照してください。

ルート要素の指定

jaxws:bindings宣言は、その他すべてのバインディング宣言のルートであり、WSDLファイルの場所およびXMLスキーマが従うネームスペースhttp://java.sun.com/xml/ns/jaxwsを定義します。

ルート宣言は次の形式で指定します。

<jaxws:bindings
wsdlLocation="uri_of_wsdl"
jaxws:xmlns="http://java.sun.com/xml/ns/jaxws">

uri_of_wsdlにWSDLファイルのURIを指定します。

表5-5で定義しているパッケージ、ラッパー形式、および非同期性マッピングのカスタマイズは、外部カスタマイズ・ファイルにおけるルート・バインディング宣言の一部として「グローバル」に定義できます。グローバル・バインディングは、wsdlLocation属性によって参照されるWSDL内のwsdl:definitionのスコープ全体に適用されます。

次に、パッケージ名、ラッパー形式、非同期マッピングのカスタマイズを定義するルート・バインディング要素の例を示します。

<jaxws:bindings
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation="http://localhost:7001/simple/SimpleService?WSDL"
xmlns:jaxws="http://java.sun.com/xml/ns/jaxws">
<package name="example.webservices.simple.simpleservice">
<enableWrapperStyle>true</enableWrapperStyle>
<enableAsyncMapping>false</enableAsyncMapping>
</jaxws:bindings>

子要素の指定

ルートのjaxws:bindings要素には、子要素を含めることができます。カスタマイズしているWSDLノードは、node属性でXPath式を渡すことによって指定します。

コンパイルされたWSDLファイル内に埋め込まれたXMLスキーマは、標準のJAXBバインディングを使用してカスタマイズすることができます。詳細は、JAX-WS WSDL Customizations (http://jax-ws.java.net/nonav/2.1.2/docs/customizations.html)の「XML Schema Customization」を参照してください。定義可能なカスタムJAXBバインディング宣言については、「JAXBカスタム・バインディング宣言」を参照してください。

たとえば、次の例では、WSDLドキュメントのwsdl:definitionsノードのパッケージ名をexamples.webservices.complex.complexserviceとして定義しています。

<jaxws:bindings
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation="http://localhost:7001/simple/SimpleService?WSDL
xmlns:jaxws="http://java.sun.com/xml/ns/jaxws">
<jaxws:bindings node="wsdl:definitions"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">
<jaxws:package name="examples.webservices.simple.simpleservice"/>
</bindings>

JAXBバインディング宣言を使用した外部バインディング宣言ファイルの作成

JAXBバインディング宣言ファイルは、ネームスペースhttp://java.sun.com/xml/ns/jaxbのXMLスキーマに従うXMLドキュメントです。以下の項では、JAXBバインディング宣言ファイルのルート要素および子要素の指定方法について説明します。定義可能なカスタム・バインディング宣言については、「JAXBカスタム・バインディング宣言」を参照してください。

ルート要素の指定

jaxb:bindings宣言は、その他すべてのバインディング宣言のルートであり、ルート宣言は次の形式で指定します。

<jaxb:bindings
schemaLocation="uri_of_schema">

uri_of_schemaにXMLスキーマ・ファイルのURIを指定します。

子要素の指定

ルートのjaxb:bindings要素には、子要素を含めることができます。カスタマイズしているスキーマ・ノードは、node属性でXPath式を渡すことによって指定します。

たとえば、次の例では、パッケージ名をexamples.webservices.simple.simpleserviceとして定義しています。

<jaxb:bindings
schemaLocation="simpleservice.xsd">
<jaxb:bindings node="//xs:simpleType[@name='value1']">
<jaxb:package name="examples.webservices.simple.simpleservice"/>
</jaxb:bindings>
</jaxb:bindings>

バインディング宣言の埋込み

バインディング宣言は、以下のいずれかの方法でWSDLファイルに埋め込むことができます。

- WSDL拡張としてjaxws:bindings要素を使用し、JAX-WSまたはJAXBバインディング宣言をWSDLファイルに埋め込みます。「WSDLファイルへのJAX-WSまたはJAXBバインディング宣言の埋め込み」を参照してください。

- <appinfo>要素の一部として、JAXBバインディング宣言をXMLスキーマに埋め込みます。「XMLスキーマへのJAXBバインディング宣言の埋め込み」を参照してください。

WSDLファイルへのJAX-WSまたはJAXBバインディング宣言の埋め込み

バインディング宣言は、WSDL拡張としてjaxws:bindings要素を使用してWSDLファイルに埋め込むことができます。定義可能なカスタム・バインディング宣言については、「JAX-WSカスタム・バインディング宣言」を参照してください。

たとえば、次の例では、SimpleServiceImplサービス・エンドポイント・インタフェース(またはポート)のクラス名をSimpleServiceとして定義しています。

<wsdl:portType name="SimpleServiceImpl">
<jaxws:bindings xmlns:jaxws="http://java.sun.com/xml/ns/jaxws">
<jaxws:class name="SimpleService"/>
</jaxws:bindings>
</wsdl:portType>

このバインディング宣言を指定しなかった場合、サービス・エンドポイント・インタフェースのデフォルト・クラス名は、wsdl:portType名、すなわちSimpleServiceImplに設定されます。

コンパイルされたWSDLファイル内に埋め込まれたXMLスキーマは、標準のJAXBバインディングを使用してカスタマイズすることができます。詳細は、JAX-WS WSDL Customizations (http://jax-ws.java.net/nonav/2.1.2/docs/customizations.html)の「XML Schema Customizations」を参照してください。定義可能なカスタムJAXBバインディング宣言については、「JAXBカスタム・バインディング宣言」を参照してください。

XMLスキーマへのJAXBバインディング宣言の埋め込み

JAXBカスタム宣言は、次に示すようにXMLスキーマの<appinfo>要素内に埋め込むことができます。

<xs:annotation>
<xs:appinfo>
<binding declaration>
</xs:appinfo>
</xs:annotation>

たとえば、次の例では、スキーマのパッケージ名を定義しています。

<schema xmlns="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://www.w3.org/2001/XMLSchema"
xmlns:jaxb="http://java.sun.com/xml/ns/jaxb"
jaxb:version="2.0">
<annotation>
<appinfo>
<jaxb:schemaBindings>
<jaxb:package name="example.webservices.simple.simpleservice"/>
</jaxb:schemaBindings>
</appinfo>
</annotation>
</schema>

JAX-WSカスタム・バインディング宣言

次の表に、一般的なJAX-WSのカスタマイズをまとめます。JAX-WSカスタム・バインディング宣言の完全なリストについては、http://jax-ws.java.net/nonav/2.1.2/docs/customizations.htmlにあるJAX-WS WSDL Customizationを参照してください。

表5-13 JAX-WSカスタム・バインディング宣言

カスタマイズ

説明

パッケージ名

パッケージ名の定義には、jaxws:packageバインディング宣言を使用します。

このカスタマイズを指定しない場合、wsdlc Antタスクが、WSDLのtargetNamespaceに基づいてパッケージ名を生成します。このデータ・バインディングのカスタマイズは、wsdlc、jwsc、またはclientgen AntタスクのpackageName属性によってオーバーライドされます。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のwsdlcに関する項を参照してください。

このバインディング宣言は、「外部バインディング宣言ファイルの作成」で説明するようにルート・バインディング要素の一部として指定したり、次の例で示すようにwsdl:definitionsノード上で指定することができます。

<bindings
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation=
"http://localhost:7001/simple/SimpleService?WSDL"
xmlns="http://java.sun.com/xml/ns/jaxws">
<bindings node="wsdl:definitions"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">
<package name="example.webservices.simple.simpleService"/>
</bindings>

ラッパー形式規則

WSDL操作のパラメータや戻り値の型の生成方法を制御するラッパー形式規則を有効化または無効化するには、jaxws:enablesWrapperStyleバインディング宣言を使用します。

このバインディング宣言は、「外部バインディング宣言ファイルの作成」で説明するようにルート・バインディング要素の一部として指定したり、以下のいずれかのノード上で指定することができます。

- wsdl:definitions - すべてのwsdl:portType属性のすべてのwsdl:operationsに適用されます。

- wsdl:portType - wsdl:portType内のすべてのwsdl:operationsに適用されます。

- wsdl:operation - wsdl:operationにのみ適用されます。

次の例では、wsdl:definitionsノードのラッパー形式規則を無効化しています。

<bindings
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation="http://localhost:7001/simple/SimpleService?WSDL"
xmlns="http://java.sun.com/xml/ns/jaxws">
<bindings node="wsdl:definitions"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">
<enableWrapperStyle>
false
</enableWrapperStyle>
</bindings>

非同期性

WSDLファイルのコンパイル時にclientgen Antタスクに、通常の同期メソッドとともに非同期のポーリング操作およびコールバック操作を生成させるには、jaxws:enableAsycMappingバインディング宣言を使用します。

このバインディング宣言は、「外部バインディング宣言ファイルの作成」で説明するようにルート・バインディング要素の一部として指定したり、以下のいずれかのノード上で指定することができます。

- wsdl:definitions - すべてのwsdl:portType属性のすべてのwsdl:operationsに適用されます。

- wsdl:portType - wsdl:portType内のすべてのwsdl:operationsに適用されます。

- wsdl:operation - wsdl:operationにのみ適用されます。

次の例では、非同期のポーリング操作およびコールバック操作を無効化しています。

<bindings
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation="http://localhost:7001/simple/SimpleService?WSDL"
xmlns="http://java.sun.com/xml/ns/jaxws">
<bindings node="wsdl:definitions"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/">
<enableAsyncMapping>
false
</enableAsyncMapping>
</bindings>

プロバイダ

プロバイダ・インタフェースとして一部をマークするには、jaxws:providerバインディング宣言を使用します。このバインディング宣言は、wsdl:portTypeの一部として指定できます。このバインディング宣言は、WSDLファイルから開始するサービスの開発時に適用されます。

クラス名

クラス名の定義には、jaxws:classバインディング宣言を使用します。このバインディング宣言は、以下のいずれかのノードに対して指定できます。

- wsdl:portType - インタフェース・クラス名を定義します。

- wsdl:fault - フォールト・クラス名を定義します。

- soap:headerfault - 例外クラス名を定義します。

- wsdl:service - 実装クラス名を定義します。

次の例では、実装クラスのクラス名を定義しています。

<bindings node="wsdl:definitions/wsdl:service[@name='SimpleService']">
<class name="myService"></class>
</bindings>

メソッド名

生成されたServiceクラスのポート・アクセサ・メソッドまたはサービス・エンドポイント・インタフェースの生成されたJavaメソッドの名前をカスタマイズするには、jaxws:methodバインディング宣言を使用します。

次の例では、wsdl:operation EchoHelloのJavaメソッド名を定義しています。

<bindings node="wsdl:definitions/wsdl:portType[@name='SimpleServiceImpl']/wsdl:operation[@name='EchoHello']">
<method name="Greeting"></method>
</bindings>

Javaパラメータ名

生成されたJavaメソッドのパラメータ名をカスタマイズするには、jaxws:parameterバインディング宣言を使用します。この宣言を使用すると、wsdl:portTypeのwsdl:operationのメソッド・パラメータを変更できます。

次の例では、wsdl:operation echoHelloのJavaメソッド名を定義しています。

<bindings node="wsdl:definitions/wsdl:portType[@name='SimpleServiceImpl']/wsdl:operation[@name='EchoHello']">
<parameter part="definitions/message[@name='EchoHello']/
part[@name='parameters']" element="hello"
name="greeting"/>
</bindings>

Javadoc

パッケージ、クラス、またはメソッドのJavadocテキストを指定するには、jaxws:javadocバインディング宣言を使用します。

たとえば、次の例では、メソッド・レベルでJavadocを定義しています。

<bindings node="wsdl:definitions/wsdl:portType[@name='SimpleServiceImpl']/wsdl:operation[@name='EchoHello']">
<method name="Hello">
<javadoc>Prints hello.</javadoc>
</method>
</bindings>

ハンドラ・チェーン

ハンドラをカスタマイズまたは追加するには、javaee:handlerchainバインディング宣言を使用します。インライン・ハンドラは、Web Services Metadata for the Java Platform仕様(JSR) (http://www.jcp.org/en/jsr/detail?id=181)で定義されているハンドラ・チェーン構成に従う必要があります。

JAXBカスタム・バインディング宣言

次の表に、一般的なJAXBのカスタマイズをまとめます。

注意:
次の表には、開始時に役立つJAXBカスタム・バインディング宣言のみをまとめています。すべてのJAXBカスタム・バインディング宣言の完全なリストと説明については、JAXB仕様(http://jcp.org/en/jsr/detail?id=222)またはJava EE 5 Tutorialの「Customizing JAXB Bindings」を参照してください。

表5-14 JAXBカスタム・バインディング宣言

カスタマイズ

説明

グローバル・バインディング

グローバル・スコープでバインディング宣言を定義するには、<globalBindings>バインディング宣言を使用します(図5-2を参照)。

<globalBindings>バインディング宣言には属性および要素を指定することができます。たとえば、以下のバインディング宣言では次の属性および要素を定義しています。

- collectionType属性 - java.util.Listインタフェースを実装し、生成される実装内のすべてのリストを表すために使用される型クラスmyArrayを指定します。

- generateIsSetMethod属性 - ゲッターおよびセッター・プロパティ・メソッドに対応するisSet()メソッドを生成します。

- javaType要素: XMLスキーマのアトミック・データ型とJavaデータ型(組込みデータ型またはアプリケーション固有のデータ型)のバインディングをカスタマイズします。

<jaxb:globalBindings
collectionType ="java.util.myArray"
generateIsSetMethod="false">
<jaxb:javaType name="java.util.Date"
xmlType="xsd:date"
</jaxb:javaType>
</jaxb:globalBindings>

スキーマ・バインディング

スキーマ・スコープでバインディング宣言を定義するには、<schemaBindings>バインディング宣言を使用します(図5-2を参照)。

例として、次の表の「パッケージ名」に関する説明を参照してください。

パッケージ名

スキーマのパッケージ名を定義するには、<schemaBindings>バインディング宣言の<package>要素を使用します(表5-12を参照)。

このカスタマイズを指定しない場合、wsdlc Antタスクが、WSDLのtargetNamespaceに基づいてパッケージ名を生成します。このデータ・バインディングのカスタマイズは、wsdlc、jwsc、またはclientgen AntタスクのpackageName属性によってオーバーライドされます。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のwsdlcに関する項を参照してください。

たとえば、次の例では、simpleservice.xsdファイルから生成されるすべてのJAXBクラスのパッケージ名を定義しています。

<jaxb:bindings
xmlns:xs="http://www.w3.org/2001/XMLSchema"
schemaLocation="simpleservice.xsd"
node="/xs:schema">
<jaxb:schemaBindings>
<jaxb:package name="examples.jaxb"/>
</jaxb:schemaBindings>
</jaxb:bindings>

次に、インポートされたXMLスキーマのパッケージ名を定義する方法を示します。

<jaxb:bindindgs
xmlns:xs="http://www.w3.org/2001/XMLSchema"
node="//xs:schema/xs:import[@namespace='http://examples.webservices.org/complexservice']">
<jaxb:schemaBindings>
<jaxb:package name="examples.jaxb"/>
</jaxb:schemaBindings>
</jaxb:bindings>

クラス名

スキーマ要素のクラス名を定義するには、<class>バインディング宣言を使用します。

次の例では、xsd:complexTypeのクラス名を定義しています。

<xs:complexType name="ComplexType">
<xs:annotation><xs:appinfo>
<jaxb:javadoc>This is my class.</jaxb:javadoc>
</jaxb:class>
</xs:appinfo></xs:annotation>
</xs:complexType>

Javaプロパティ名

スキーマ要素のプロパティ名を定義するには、<property>バインディング宣言を使用します。

次の例では、Javaプロパティ名を定義する方法について説明します。

<jaxb:bindindgs
xmlns:xs="http://www.w3.org/2001/XMLSchema"
node="//xs:schema/">
<jaxb:schemaBindings>
<jaxb:property generateIsSetMethod="true"/>
</jaxb:schemaBindings>
</jaxb:bindings>

Javaデータ型

XMLスキーマのアトミック・データ型とJavaデータ型(組込みデータ型またはアプリケーション固有のデータ型)のバインディングをカスタマイズするには、<javaType>バインディング宣言を使用します。

たとえば、グローバル・バインディング(上記の)を参照してください。

Javadoc

要素のJavadocを指定するには、<class>または<property>バインディング宣言の<javadoc>子要素を使用します。

例:

<xs:complexType name="ComplexType">
<xs:annotation><xs:appinfo>
<jaxb:class name="MyClass">
<jaxb:javadoc>This is my class.</jaxb:javadoc>
</jaxb:class>
</xs:appinfo></xs:annotation>
</xs:complexType>

Glassfish RI JAXBデータ・バインディング・プロバイダおよびJAXBプロバイダの使用

Glassfish RI JAXBデータ・バインディング・プロバイダおよびJAXBプロバイダは、標準のGlassfish JAXB実装を提供します。これは、以前のWebLogic ServerリリースではデフォルトのJAXBプロバイダでした。必要に応じてサーバー全体またはアプリケーション単位でGlassfish RIプロバイダをリストアできます。

JAXBデータ・バインディング・プロバイダおよびJAXBプロバイダは、いずれもEclipseLink MOXyをデフォルトで使用しますが、2つの異なるエンティティです。JAXBデータ・バインディング・プロバイダは、Webサービス・ツールおよびランタイムによって使用され、JavaエンドポイントからのWSDL生成などのタスクをJWSタスクで行われるのと同様に実行します。また、SOAPメッセージのコンテンツを実行時にマーシャリングおよびアンマーシャリングします。一方、JAXBプロバイダは、他のすべてのJAXB関連タスクに使用するJAXBContextプロバイダを指定します。JAXBプロバイダの構成は、一部のWebサービス・ツール(WSDLファイルおよびスキーマ・ファイルからのJavaクラスの生成など)に適用されますが、他のすべてのJAXBの用途も含まれます。これらの2つのプロバイダは個別に構成可能です。たとえば、データ・バインディングではEclipseLink MOXyを保持し、他のJAXBタスクではGlassfish RI JAXBプロバイダに戻すことができます。

データ・バインディングおよびJAXBプロバイダは、MW_HOME/oracle_common/modules/com.oracle.webservices.wls.wls-ws-metainf-services-impl_12.1.3.jarに含まれる次のJava Service Provider Interface(SPI)ファイルを使用して構成します。

- META-INF/services/com.sun.xml.ws.spi.db.BindingContextFactory

- META-INF/services/javax.xml.bind.JAXBContext

注意:
12.1.2.0では、プロバイダはMW_HOME/oracle_common/modules/com.oracle.webservices.wls.wls-ws-metainf-services_2.0.0.0.jarにありました。12.1.1.0では、プロバイダはWL_HOME/server/lib/weblogic.jarにありました。

全体レベルおよびアプリケーション・レベルでの構成については次の項で説明します。

サーバー全体レベルでのデータ・バインディングおよびJAXBプロバイダの構成

WebLogic Serverディストリビューションには、デフォルトのデータ・バインディング構成のオーバーライドを簡単にするために、次のjarファイルが用意されています。

modules/databinding.override_1.0.0.0.jar

このjarファイルは、デフォルトではクラスパスに含まれていません。Glassfish RIデータ・バインディングおよびJAXBプロバイダの設定をリストアするには、WebLogic Serverの開始スクリプトを編集してこのjarファイルをクラスパスに付加します。

ツールおよびクライアントでは、このjarファイルをAntスクリプトまたは別のビルド環境全体に適用できます。

databinding.override_1.0.0.0.jarファイルはデータ・バインディング・プロバイダとJAXBプロバイダの両方をオーバーライドすることに注意してください。これらのプロバイダの両方ではなく、いずれかをオーバーライドする場合は、オーバーライドするサービス・プロバイダのエントリのみを含む簡単なjarファイルを作成し、このファイルをクラスパスで先に配置することで実現できます。

たとえば、Glassfish RI JAXBプロバイダのみを構成するには次のようにします。

1. META-INF/services/javax.xml.bind.JAXBContextという名前のファイルを作成し、次のGlassfish RI JAXBプロバイダの単一エントリを含めます。

com.sun.xml.bind.v2.ContextFactory

2. jarファイル(jaxb_override.jarなど)を作成し、ステップ1で作成したファイルを追加します。

3. Glassfish JAXBプロバイダを使用するクラスパスにこのjarファイルを付加します。

Glassfish RIデータ・バインディング・プロバイダのみを構成する場合も同じ手順を適用します。ただしこの場合、ステップ1で作成するファイルの名前をMETA-INF/services/com.sun.xml.ws.spi.db.BindingContextFactoryとし、次のGlassfish RIデータ・バインディング・プロバイダの単一エントリを含めます。

com.sun.xml.ws.db.glassfish.JAXBRIContextFactory.

注意:
データ・バインディング・プロバイダを構成すると、実行時のデータ・バインディングに加えて他の動作にも影響が及ぶ場合があります。たとえば、WebLogic Serverは実行時にデータ・バインディング・プロバイダを使用してWSDLを生成します。一方で、JAXBプロバイダを直接呼び出すと、実行時にSOAPフォルトが発生する場合があります。

オーバーライド用のjarファイルをクラスパスに配置するかわりに、Javaシステム・プロパティを直接編集できます。詳細は、「JAXB用Javaシステム・プロパティの構成」を参照してください。

アプリケーション・レベルでのデータ・バインディングおよびJAXBプロバイダの構成

単一のWebアプリケーションのデータ・バインディングおよびJAXBプロバイダを構成するには、WebLogic Serverが提供するフィルタリング・ロード・メカニズムを使用します。このメカニズムを使用すると、アプリケーションのクラスパスにある特定のアプリケーション・クラスとリソースを検索するときにシステム・クラスパスの検索を省略できます。具体的には、そのアプリケーションのEARまたはビルド出力ディレクトリのweblogic-application.xmlファイルで<prefer-application-resources>タグを使用します。

たとえば、アプリケーションに対してGlassfish RIデータ・バインディング・プロバイダを構成するには次のようにします。

1. 次の例に示すように、weblogic-application.xmlファイルを編集して、データ・バインディング・リソースのエントリを含めます。

<prefer-application-resources> <resource-name>META-INF/services/com.sun.xml.ws.spi.db.BindingContextFactory</resource-name>
</prefer-application-resources>

2. META-INF/services/com.sun.xml.ws.spi.db.BindingContextFactoryという名前のファイルを作成し、対象プロバイダのエントリを含めます。この場合は、com.sun.xml.ws.db.glassfish.JAXBRIContextFactoryです。

3. ステップ2で作成したファイルをビルド出力ディレクトリに追加するか、EARファイルのエントリとして追加します。

Glassfish RI JAXBプロバイダを構成するには、同じ手順でJAXBプロバイダに適した値を使用します。具体的には、リソース名META-INF/services/javax.xml.bind.JAXBContextをweblogic-application.xmlファイルに追加し、このファイルのプロバイダ名にcom.sun.xml.bind.v2.ContextFactoryを設定します。

WebLogic Serverにおけるフィルタリング・ロード・メカニズムの詳細は、『Oracle WebLogic Serverのパフォーマンスのチューニング』のフィルタリング・ローダー・メカニズムに関する項を参照してください。

JAXB用Javaシステム・プロパティの構成

Javaシステム・プロパティを構成してGlassfish RIプロバイダに戻したり、すでに戻されている場合はデフォルトのEclipseLink MOXyプロバイダを構成したりすることができます。

注意:
ある特定の状況では、間接的に呼び出されたJavaインスタンス(Antタスクからフォークされたクライアントなど)へのシステム・プロパティの伝播が困難な場合があります。このような場合、使用している環境でプロパティが確実に伝播されるようにする必要があります。

Glassfish RIデータ・バインディングおよびJAXBプロバイダを構成するには、表5-15に示すようにJavaシステム・プロパティを設定します。

表5-15 Glassfish RIプロバイダ用のJavaシステム・プロパティの設定

対象Javaシステム・プロパティ

設定値

com.sun.xml.ws.spi.db.BindingContextFactory

com.sun.xml.ws.db.glassfish.JAXBRIContextFactory

javax.xml.bind.JAXBContext

com.sun.xml.bind.v2.ContextFactory

デフォルトのEclipseLink MOXyプロバイダを構成するには、表5-16に示すようにJavaシステム・プロパティを設定します。

表5-16 EclipseLink MOXyプロバイダ用のJavaシステム・プロパティの設定

対象Javaシステム・プロパティ

設定値

com.sun.xml.ws.spi.db.BindingContextFactory

com.sun.xml.ws.db.toplink.JAXBContextFactory

javax.xml.bind.JAXBContext

org.eclipse.persistence.jaxb.JAXBContextFactory

6 JAX-WS Webサービスの開発例

この章では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの一般的な開発例を示します。

この章の内容は次のとおりです:

- 簡単なHelloWorld Webサービスの作成

- ユーザー定義のデータ型を使用するWebサービスの作成

- WSDLファイルからのWebサービスの作成

各例では、簡単なWebLogic Webサービスを作成する手順や、デプロイ済のWebサービスから操作を呼び出す手順を示します。これらの例には基本的なJavaコードとAnt build.xmlファイルが含まれており、それらをユーザーの開発環境で使用してサンプルを再現することや、現在の開発環境とは別の環境で指示に従ってサンプルを作成して実行することができます。

例ではサンプルで使用されるプロセスやツールについては詳しく説明していません。詳細は、以降の章を参照してください。

注意:
高度なWebサービス機能を示すベスト・プラクティスの例については、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」および第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

簡単なHelloWorld Webサービスの作成

この項では、操作が1つの非常に簡単なWebサービスの作成方法について説明します。Webサービスを実装するJava Webサービス(JWS)・ファイルでは必須のJWSアノテーション@WebServiceを1つのみ使用しています。JWSファイルは、JWSメタデータ・アノテーションを使用してWebサービスの形式を指定した標準のJavaファイルです。メタデータ・アノテーションはJDK 5.0で導入され、Webサービス・ファイルにアノテーションを付けるために使用される一連のアノテーションはJWSアノテーションと呼ばれます。WebLogic Webサービスは標準のJWSアノテーションを使用します。サポートされるJWSアノテーションの完全なリストは、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスのアノテーション・サポートに関する項を参照してください。

次の例では、1つの操作sayHelloWorldを含むHelloWorldServiceというWebサービスを作成する方法を示します。簡単にするために、操作は入力された文字列値を戻すものとします。

1. WebLogic Server環境を設定します。
コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)スクリプトを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2. 次のようにプロジェクト・ディレクトリを作成します。

prompt> mkdir /myExamples/hello_world

3. プロジェクト・ディレクトリの下に、srcディレクトリと、JWSファイル(この手順で後述)のパッケージ名に対応するサブディレクトリを作成します。

prompt> cd /myExamples/hello_world
prompt> mkdir src/examples/webservices/hello_world

4. Webサービスを実装するJWSファイルを作成します。
任意のJava IDEまたはテキスト・エディタを開いて、「サンプルHelloWorldImpl.java JWSファイル」で指定されたJavaコードを使用してHelloWorldImpl.javaというJavaファイルを作成します。

サンプルJWSファイルでは、1つのパブリック・メソッドsayHelloWorld(String)を含むHelloWorldImplというJavaクラスが示されています。@WebServiceアノテーションは、JavaクラスがHelloWorldServiceというWebサービスを実装することを指定しています。デフォルトでは、すべてのパブリック・メソッドが操作として公開されます。

5. src/examples/webservices/hello_worldディレクトリにHelloWorldImpl.javaファイルを保存します。

6. プロジェクト・ディレクトリ(myExamples/hello_world/src)内に標準のAnt build.xmlファイルを作成し、taskdef Antタスクを追加して、jwscタスクの完全修飾Javaクラス名を指定します。

<project name="webservices-hello_world" default="all">
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
</project>

この手順で説明される追加のターゲット(clean、undeploy、client、およびrunなど)が含まれている、完全なサンプルbuild.xmlファイルについては、「HelloWorldImpl.javaのサンプルAntビルド・ファイル」を参照してください。完全なbuild.xmlファイルでは、EARディレクトリの名前を常にハード・コード化して使用するのではなく、${ear-dir}などのプロパティも使用しています。

7. 次のようなjwsc Antタスクの呼出しを、build-serviceターゲット内にラップして、build.xmlファイルに追加します。

<target name="build-service">
<jwsc
srcdir="src"
destdir="output/helloWorldEar">
<jws file="examples/webservices/hello_world/HelloWorldImpl.java"
type="JAXWS"/>
</jwsc>
</target>

jwsc WebLogic WebサービスAntタスクは、補助的なアーティファクトを生成し、ユーザーが作成および生成したJavaコードをコンパイルして、すべてのアーティファクトを、後でWebLogic Serverにデプロイされるエンタープライズ・アプリケーションEARファイルにアーカイブ化します。type="JAXWS"を使用して作成するWebサービス(JAX-WS)のタイプを指定します。

8. コマンド・ラインでbuild-serviceターゲットを指定して、jwsc Antタスクを実行します。

prompt> ant build-service

output/helloWorldEarディレクトリを見て、jwsc Antタスクによって生成されたファイルとアーティファクトを確認します。

9. WebサービスをデプロイするWebLogic Serverインスタンスを起動します。

10. WebLogic Server管理コンソールまたはwldeploy Antタスクを使用して、エンタープライズ・アプリケーションにパッケージ化されたWebサービスをWebLogic Serverにデプロイします。いずれの場合でも、outputディレクトリにあるhelloWorldEarエンタープライズ・アプリケーションをデプロイします。
wldeploy Antタスクを使用するには、以下のターゲットをbuild.xmlファイルに追加します。

<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="deploy">
<wldeploy action="deploy"
name="helloWorldEar" source="output/helloWorldEar"
user="${wls.username}" password="${wls.password}"
verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>

wls.username、wls.password、wls.hostname、wls.port、およびwls.server.nameの値は、ご使用のWebLogic Serverインスタンスの対応する値で置き換えます。

deployターゲットを実行して、WARファイルをデプロイします。

prompt> ant deploy

11. ブラウザでWSDLを呼び出して、Webサービスが正しくデプロイされていることをテストします。

http://host:port/HelloWorldImpl/HelloWorldService?WSDL

URLは、contextPathおよびserviceUri属性のデフォルト値を使用して構築します。contextPathのデフォルト値はJWSファイル内のJavaクラスの名前です。serviceURI属性のデフォルト値は@WebServiceアノテーションのserviceName要素です(指定されている場合)。そうでない場合、拡張子を除いたJWSファイルの名前の後にServiceを付けたものになります。たとえば、@WebServiceアノテーションのserviceName要素が指定されておらず、JWSファイルの名前がHelloWorldImpl.javaである場合、そのserviceUriのデフォルト値はHelloWorldImplServiceになります。

これらの属性は、次の「ユーザー定義のデータ型を使用したWebサービスの作成」の例で明示的に設定されます。各自のWebLogic Serverインスタンスに適合したホスト名およびポートを選択してください。

build.xmlファイルでclean、build-service、undeploy、deployの各ターゲットを使用すると、開発プロセスの一環としてWebサービスの更新、再ビルド、アンデプロイおよび再デプロイを繰り返し実行できます。

Webサービスを実行するには、そのWebサービスを呼び出すクライアントを作成する必要があります。Webサービスを呼び出すJavaクライアント・アプリケーションの作成例については、「WebLogic WebサービスからのWebサービスの呼出し」を参照してください。

サンプルHelloWorldImpl.java JWSファイル

package examples.webservices.hello_world;
// Import the @WebService annotation
import javax.jws.WebService;
@WebService(name="HelloWorldPortType", serviceName="HelloWorldService")
/**
* This JWS file forms the basis of simple Java-class implemented WebLogic
* Web Service with a single operation: sayHelloWorld
*/
public class HelloWorldImpl {
// By default, all public methods are exposed as Web Services operation
public String sayHelloWorld(String message) {
try {
System.out.println("sayHelloWorld:" + message);
} catch (Exception ex) { ex.printStackTrace(); }

return "Here is the message: '" + message + "'";
}
}

HelloWorldImpl.javaのサンプルAntビルド・ファイル

以下のbuild.xmlファイルでは、プロパティを使用してファイルを簡素化しています。

<project name="webservices-hello_world" default="all">
<!-- set global properties for this build -->
<property name="wls.username" value="weblogic" />
<property name="wls.password" value="weblogic" />
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="wls.server.name" value="myserver" />
<property name="ear.deployed.name" value="helloWorldEar" />
<property name="example-output" value="output" />
<property name="ear-dir" value="${example-output}/helloWorldEar" />
<property name="clientclass-dir" value="${example-output}/clientclasses" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="all" depends="clean,build-service,deploy,client" />
<target name="clean" depends="undeploy">
<delete dir="${example-output}"/>
</target>
<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}">
<jws file="examples/webservices/hello_world/HelloWorldImpl.java"
type="JAXWS"/>
</jwsc>
</target>
<target name="deploy">
<wldeploy action="deploy" name="${ear.deployed.name}"
source="${ear-dir}" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="undeploy">
<wldeploy action="undeploy" name="${ear.deployed.name}"
failonerror="false"
user="${wls.username}" password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/HelloWorldImpl/HelloWorldService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.hello_world.client"
type="JAXWS"/>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/hello_world/client/**/*.java"/>
</target>
<target name="run">
<java classname="examples.webservices.hello_world.client.Main"
fork="true" failonerror="true" >
<classpath refid="client.class.path"/>
<arg
line="http://${wls.hostname}:${wls.port}/HelloWorldImpl/HelloWorldService"  />
</java> </target>
</project>

ユーザー定義のデータ型を使用するWebサービスの作成

前の例では、Webサービス操作のパラメータと戻り値として、単純データ型Stringのみを使用していました。次の例では、ユーザー定義のデータ型(特にBasicStructというJavaBean)を操作のパラメータおよび戻り値として使用するWebサービスの作成方法を示します。

Webサービスでユーザー定義のデータ型を使用する場合、データ型のJavaソースを作成して、それをJWSファイル内で適切に使用する以外に、プログラマが実際にすべきことはほとんどありません。jwsc Antタスクは、JWSファイルにユーザー定義のデータ型がある場合、XML表現(SOAPメッセージで使用)とJava表現(WebLogic Serverで使用)との間でデータを変換するのに必要な、すべてのデータ・バインディング・アーティファクトを自動的に生成します。データ・バインディング・アーティファクトには、Javaユーザー定義データ型に相当するXMLスキーマがあります。

次の手順は「簡単なHelloWorld Webサービスの作成」に記載されている手順によく似ています。そのため、手順では必要なステップをすべて示していますが、簡単なHelloWorldサンプルとは異なるステップのみの詳細を説明しています。

1. WebLogic Server環境を設定します。
コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)スクリプトを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2. プロジェクト・ディレクトリを作成します。

prompt> mkdir /myExamples/complex

3. プロジェクト・ディレクトリの下に、srcディレクトリと、JWSファイル(この手順で後述)のパッケージ名に対応するサブディレクトリを作成します。

prompt> cd /myExamples/complex
prompt> mkdir src/examples/webservices/complex

4. BasicStruct JavaBeanのソースを作成します。
任意のJava IDEまたはテキスト・エディタを開いて、「サンプルBasicStruct JavaBean」で指定されたJavaコードを使用して BasicStruct.javaというJavaファイルをプロジェクト・ディレクトリに作成します。

5. BasicStruct.javaファイルをプロジェクト・ディレクトリのsrc/examples/webservices/complexサブディレクトリに保存します。

6. 「サンプルComplexImpl.java JWSファイル」で指定されたJavaコードを使用して、Webサービスを実装するJWSファイルを作成します。
このサンプルJWSファイルでは、複数のJWSアノテーションを使用しています。@WebMethodでは、メソッドがWebサービス操作として公開されることを明示的に指定し、操作名をデフォルトのメソッド名echoStructからechoComplexTypeに変更します。@WebParamと@WebResultでは、パラメータと戻り値を構成します。@SOAPBindingでは、Webサービスのタイプを指定します。また、ComplexImpl.java JWSファイルではexamples.webservice.complex.BasicStructクラスをインポートして、echoStruct()メソッドのパラメータと戻り値としてユーザー定義データ型のBasicStructを使用します。

JWSファイルの作成に関するより詳細な情報については、第4章「JWSファイルのプログラミング」を参照してください。

7. ComplexImpl.javaファイルをプロジェクト・ディレクトリのsrc/examples/webservices/complexサブディレクトリに保存します。

8. プロジェクト・ディレクトリ内に標準のAnt build.xmlファイルを作成し、taskdef Antタスクを追加して、jwscタスクの完全修飾クラス名を指定します。

<project name="webservices-complex" default="all">
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
</project>

完全なサンプルbuild.xmlファイルについては、「ComplexImpl.java JWSファイルのサンプルAntビルド・ファイル」を参照してください。

9. 次のようなjwsc Antタスクの呼出しを、build-serviceターゲット内にラップして、build.xmlファイルに追加します。

<target name="build-service">
<jwsc
srcdir="src"
destdir="output/ComplexServiceEar" >
<jws file="examples/webservices/complex/ComplexImpl.java"
type="JAXWS">
<WLHttpTransport
contextPath="complex" serviceUri="ComplexService"
portName="ComplexServicePort"/>
</jws>
</jwsc>
</target>

上記の例で注目すべき点は以下のとおりです。

- <jws>要素のtype属性では、Webサービスのタイプ(JAX-WSまたはJAX-RPC)が指定されています。

- jwsc Antタスクの<jws>要素の<WLHttpTransport>子要素では、HTTP/Sトランスポートを介してWebサービスを呼び出す際に使用されるURLのコンテキスト・パスとサービスURIセクションに加え、生成されるWSDLのポートの名前も指定されています。コンテキスト・パスの定義の詳細は、「WebLogic Webサービスのコンテキスト・パスの定義」を参照してください。

10. jwsc Antタスクを使用します。

prompt> ant build-service

output/ComplexServiceEarディレクトリを見て、jwsc Antタスクによって生成されたファイルとアーティファクトを確認します。

11. WebサービスをデプロイするWebLogic Serverインスタンスを起動します。

12. WebLogic Server管理コンソールまたはwldeploy Antタスクを使用して、ComplexServiceEarエンタープライズ・アプリケーションにパッケージ化されたWebサービスをWebLogic Serverにデプロイします。例:

prompt> ant deploy

13. WebLogic Server管理コンソールまたはwldeploy Antタスクを使用して、エンタープライズ・アプリケーションにパッケージ化されたWebサービスをWebLogic Serverにデプロイします。いずれの場合でも、outputディレクトリにあるComplexServiceEarエンタープライズ・アプリケーションをデプロイします。
wldeploy Antタスクを使用するには、以下のターゲットをbuild.xmlファイルに追加します。

<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="deploy">
<wldeploy action="deploy"
name="ComplexServiceEar" source="output/ComplexServiceEar"
user="${wls.username}" password="${wls.password}"
verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>

wls.username、wls.password、wls.hostname、wls.port、およびwls.server.nameの値は、ご使用のWebLogic Serverインスタンスの対応する値で置き換えます。

deployターゲットを実行して、WARファイルをデプロイします。

prompt> ant deploy

14. ブラウザでWSDLを呼び出して、Webサービスが正しくデプロイされていることをテストします。

http://host:port/complex/ComplexService?WSDL

Webサービスを実行するには、そのWebサービスを呼び出すクライアントを作成する必要があります。Webサービスを呼び出すJavaクライアント・アプリケーションの作成例については、「WebLogic WebサービスからのWebサービスの呼出し」を参照してください。

サンプルのBasicStruct JavaBean

package examples.webservices.complex;
/**
* Defines a simple JavaBean called BasicStruct that has integer, String,
* and String[] properties
*/
public class BasicStruct {
// Properties
private int intValue;
private String stringValue;
private String[] stringArray;
// Getter and setter methods
public int getIntValue() {
return intValue;
}
public void setIntValue(int intValue) {
this.intValue = intValue;
}
public String getStringValue() {
return stringValue;
}
public void setStringValue(String stringValue) {
this.stringValue = stringValue;
}
public String[] getStringArray() {
return stringArray;
}
public void setStringArray(String[] stringArray) {
this.stringArray = stringArray;
}
public String toString() {
return "IntValue="+intValue+", StringValue="+stringValue;
}
}

サンプルComplexImpl.java JWSファイル

package examples.webservices.complex;
// Import the standard JWS annotation interfaces
import javax.jws.WebMethod;
import javax.jws.WebParam;
import javax.jws.WebResult;
import javax.jws.WebService;
import javax.jws.soap.SOAPBinding;
// Import the BasicStruct JavaBean
import examples.webservices.complex.BasicStruct;
// Standard JWS annotation that specifies that the portType name of the Web
// Service is "ComplexPortType", its public service name is "ComplexService",
// and the targetNamespace used in the generated WSDL is "http://example.org"
@WebService(serviceName="ComplexService", name="ComplexPortType",
targetNamespace="http://example.org")
// Standard JWS annotation that specifies this is a document-literal-wrapped
// Web Service
@SOAPBinding(style=SOAPBinding.Style.DOCUMENT,
use=SOAPBinding.Use.LITERAL,
parameterStyle=SOAPBinding.ParameterStyle.WRAPPED)
/**
* This JWS file forms the basis of a WebLogic Web Service.  The Web Services
* has two public operations:
*
*  - echoInt(int)
*  - echoComplexType(BasicStruct)
*
* The Web Service is defined as a "document-literal" service, which means
* that the SOAP messages have a single part referencing an XML Schema element
* that defines the entire body.
*/
public class ComplexImpl {
// Standard JWS annotation that specifies that the method should be exposed
// as a public operation.  Because the annotation does not include the
// member-value "operationName", the public name of the operation is the
// same as the method name: echoInt.
//
// The WebResult annotation specifies that the name of the result of the
// operation in the generated WSDL is "IntegerOutput", rather than the
// default name "return".   The WebParam annotation specifies that the input
// parameter name in the WSDL file is "IntegerInput" rather than the Java
// name of the parameter, "input".
@WebMethod()
@WebResult(name="IntegerOutput",
targetNamespace="http://example.org/complex")
public int echoInt(
@WebParam(name="IntegerInput",
targetNamespace="http://example.org/complex")
int input)
{
System.out.println("echoInt '" + input + "' to you too!");
return input;
}
// Standard JWS annotation to expose method "echoStruct" as a public operation
// called "echoComplexType"
// The WebResult annotation specifies that the name of the result of the
// operation in the generated WSDL is "EchoStructReturnMessage",
// rather than the default name "return".
@WebMethod(operationName="echoComplexType")
@WebResult(name="EchoStructReturnMessage",
targetNamespace="http://example.org/complex")
public BasicStruct echoStruct(BasicStruct struct)
{
System.out.println("echoComplexType called");
return struct;
}
}

ComplexImpl.java JWSファイルのサンプルAntビルド・ファイル

以下のbuild.xmlファイルでは、プロパティを使用してファイルを簡素化しています。

<project name="webservices-complex" default="all">
<!-- set global properties for this build -->
<property name="wls.username" value="weblogic" />
<property name="wls.password" value="weblogic" />
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="wls.server.name" value="myserver" />
<property name="ear.deployed.name" value="complexServiceEAR" />
<property name="example-output" value="output" />
<property name="ear-dir" value="${example-output}/complexServiceEar" />
<property name="clientclass-dir" value="${example-output}/clientclass" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="all" depends="clean,build-service,deploy,client"/>
<target name="clean" depends="undeploy">
<delete dir="${example-output}"/>
</target>
<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}"
keepGenerated="true"
>
<jws file="examples/webservices/complex/ComplexImpl.java"
type="JAXWS">
<WLHttpTransport
contextPath="complex" serviceUri="ComplexService"
portName="ComplexServicePort"/>
</jws>
</jwsc>
</target>
<target name="deploy">
<wldeploy action="deploy"
name="${ear.deployed.name}"
source="${ear-dir}" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}"/>
</target>
<target name="undeploy">
<wldeploy action="undeploy" failonerror="false"
name="${ear.deployed.name}"
user="${wls.username}" password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}"/>
</target>
<target name="client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.complex.client"
type="JAXWS"/>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/complex/client/**/*.java"/>
</target>
<target name="run" >
<java fork="true"
classname="examples.webservices.complex.client.Main"
failonerror="true" >
<classpath refid="client.class.path"/>
<arg line="http://${wls.hostname}:${wls.port}/complex/ComplexService"
/>
</java>
</target>
</project>

WSDLファイルからのWebサービスの作成

Webサービスの作成のもう1つの一般的な例は、既存のWSDLファイル(黄金のWSDLとも呼ばれます)から開始する方法です。WSDLファイルはWebサービスがどのようなものかを指定するパブリック・コントラクトであり、サポートされる操作のリスト、各操作のシグネチャと形式、操作を呼び出すときに使用されるプロトコルとトランスポート、データをトランスポートするときに使用されるXMLスキーマ・データ型などを指定します。WSDLファイルに基づいて、WebLogic Serverにデプロイできるように、Webサービスを実装するアーティファクトを生成します。wsdlc Antタスクを使用して次のアーティファクトを生成します。

- WSDLファイルで記述されたWebサービスを実装するJWSサービス・エンドポイント・インタフェース(SEI)。

- 生成されるJWS SEIの不完全な(途中まで作成済みの)実装が含まれるJWS実装ファイル。このファイルは開発者がカスタマイズする必要があります。

- JAXBデータ・バインディング・アーティファクト。

- (オプション)生成されるJWS SEIのJavadoc。

注意:
更新することになるwsdlc Antタスクによって生成されるファイルは、JWS実装ファイルのみです。JWS SEIおよびデータ・バインディング・アーティファクトが含まれるJARファイルを更新する必要はありません。

一般に、wsdlc Antタスクを1回実行して、生成されるJWS SEIファイルとデータ・バインディング・アーティファクトを含むJARファイルを生成し、その後で、インタフェースを実装する生成済JWSファイルをコーディングして、Webサービスのビジネス・ロジックを追加します。特に、Webサービス操作を実装するメソッドに、操作の動作に必要なJavaコードを追加し、JWSアノテーションを追加します。

JWS実装ファイルをコーディングしたら、前の項で説明した同じ手順に従って、jwsc Antタスクを実行してデプロイ可能なWebサービスを生成します。相違点は、compiledWsdl属性を使用して、wsdlc Antタスクによって生成されるJARファイル(JWS SEIファイルとデータ・バインディング・アーティファクトを含む)を指定することのみです。

次の簡単な例は、「サンプルWSDLファイル」に示したWSDLファイルからWebサービスを作成する方法を示しています。このWebサービスには、郵便番号を渡されると気温を返すgetTempという1つの操作が含まれています。

1. WebLogic Server環境を設定します。
コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)スクリプトを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2. 作業ディレクトリを作成します。

prompt> mkdir /myExamples/wsdlc

3. WSDLファイルをコンピュータ上のアクセス可能なディレクトリに置きます。
この例では、WSDLファイルはTemperatureService.wsdlという名前で/myExamples/wsdlc/wsdl_filesディレクトリにあると仮定しています。ファイルの完全なリストについては、「サンプルWSDLファイル」を参照してください。

4. プロジェクト・ディレクトリ内に標準のAnt build.xmlファイルを作成し、taskdef Antタスクを追加して、wsdlcタスクの完全修飾Javaクラス名を指定します。

<project name="webservices-wsdlc" default="all">
<taskdef name="wsdlc"
classname="weblogic.wsee.tools.anttasks.WsdlcTask"/>
</project>

この手順で説明される追加のターゲット(clean、undeploy、client、およびrunなど)が含まれている、完全なサンプルbuild.xmlファイルについては、「TemperatureServiceのサンプルAntビルド・ファイル」を参照してください。完全なbuild.xmlファイルでは、EARディレクトリの名前を常にハード・コード化して使用するのではなく、${ear-dir}などのプロパティも使用しています。

5. 次のようなwsdlc Antタスクの呼出しを、generate-from-wsdlターゲット内にラップして、build.xmlファイルに追加します。

<target name="generate-from-wsdl">
<wsdlc
srcWsdl="wsdl_files/TemperatureService.wsdl"
destJwsDir="output/compiledWsdl"
destImplDir="output/impl"
packageName="examples.webservices.wsdlc"
type="JAXWS"/>
</target>

このサンプルwsdlcタスクでは、JWS SEIとデータ・バインディング・アーティファクトを含むJARファイルを、カレント・ディレクトリ下のoutput/compiledWsdlディレクトリに生成します。また、JWS SEIの部分的な実装ファイル(TemperatureService_TemperaturePortImpl.java)を、output/impl/examples/webservices/wsdlcディレクトリに生成します(このディレクトリは、destImplDirで指定された出力ディレクトリと、パッケージ名で指定されたディレクトリ階層を組み合せたものです)。生成されたすべてのJWSファイルはexamples.webservices.wsdlcパッケージにパッケージ化されます。

6. コマンド・ラインでgenerate-from-wsdlターゲットを指定して、wsdlc Antタスクを実行します。

prompt> ant generate-from-wsdl

wsdlc Antタスクによってアーティファクトとファイルが生成されたことを調べるには、outputディレクトリを確認します。

7. 任意のJava IDEまたはテキスト・エディタを使用して、生成されたoutput/impl/examples/webservices/wsdlc/TemperatureService_TemperaturePortImpl.java JWS実装ファイルを編集し、目的の処理が行えるようにメソッドにJavaコードを追加します。
例は、「TemperatureService_TemperaturePortImpl Java実装ファイルのサンプル」を参照してください。追加されたJavaコードは太字になっています。生成されたJWS実装ファイルには@WebService JWSアノテーション値が自動的に含まれており、その値は元のWSDLファイルの値に対応しています。

注意:
「WSDLから開始する」ユース・ケースのJWS実装ファイルに追加できるJWSアノテーションには制限があります。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のwsdlcに関する項を参照してください。

処理を簡単にするため、サンプルのTemperatureService_TemperaturePortImpl.javaのgetTemp()メソッドは、固定の数値を返します。実際のファイルの場合、このメソッドの実装では、特定の郵便番号で現在の気温をルックアップします。

8. 更新したTemperatureService_TemperaturePortImpl.javaファイルを永続的なディレクトリ(プロジェクト・ディレクトリの下のsrcディレクトリなど)にコピーします。パッケージ名に対応する子ディレクトリも必ず作成するようにしてください。

prompt> cd /examples/wsdlc
prompt> mkdir src/examples/webservices/wsdlc
prompt> cp output/impl/examples/webservices/wsdlc/TemperatureService_TemperaturePortImpl.java.java \src/examples/webservices/wsdlc/TemperatureService_TemperaturePortImpl.java.java

9. 更新されたJWS実装クラスに対してjwsc Antタスクを実行するbuild-serviceターゲットを、build.xmlファイルに追加します。jwscのcompiledWsdl属性を使用して、wsdlc Antタスクによって生成されるJARファイルの名前を指定します。

<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}">
<jws file="examples/webservices/wsdlc/TemperatureService_TemperaturePortImpl.java"
compiledWsdl="${compiledWsdl-dir}/TemperatureService_wsdl.jar"
type="JAXWS">
<WLHttpTransport
contextPath="temp" serviceUri="TemperatureService"
portName="TemperaturePort">
</WLHttpTransport>
</jws>
</jwsc>
</target>

上記の例で注目すべき点は以下のとおりです。

- <jws>要素のtype属性では、Webサービスのタイプ(JAX-WSまたはJAX-RPC)が指定されています。

- jwsc Antタスクの<jws>要素の<WLHttpTransport>子要素では、HTTP/Sトランスポートを介してWebサービスを呼び出す際に使用されるURLのコンテキスト・パスとサービスURIセクションに加え、生成されるWSDLのポートの名前も指定されています。

10. build-serviceターゲットを実行してデプロイ可能なWebサービスを生成します。

prompt> ant build-service

JWSファイルを更新して再ビルドする場合、このターゲットを再実行します。

11. WebサービスをデプロイするWebLogic Serverインスタンスを起動します。

12. WebLogic Server管理コンソールまたはwldeploy Antタスクを使用して、エンタープライズ・アプリケーションにパッケージ化されたWebサービスをWebLogic Serverにデプロイします。いずれの場合でも、outputディレクトリにあるwsdlcEarエンタープライズ・アプリケーションをデプロイします。
wldeploy Antタスクを使用するには、以下のターゲットをbuild.xmlファイルに追加します。

<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="deploy">
<wldeploy action="deploy" name="wsdlcEar"
source="output/wsdlcEar" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>

wls.username、wls.password、wls.hostname、wls.port、およびwls.server.nameの値は、ご使用のWebLogic Serverインスタンスの対応する値で置き換えます。

deployターゲットを実行して、WARファイルをデプロイします。

prompt> ant deploy

13. ブラウザでWSDLを呼び出して、Webサービスが正しくデプロイされていることをテストします。

http://host:port/temp/TemperatureService?WSDL

上記のURLのコンテキスト・パスとサービスURIの部分は元の黄金のWSDLで指定されています。WebLogic Serverインスタンスのホスト名とポートを使用します。デプロイされたWSDLファイルと元のWSDLファイルは、エンドポイント・アドレスのホストとポート以外は同じであることに注目してください。

build.xmlファイルでclean、build-service、undeploy、deployの各ターゲットを使用すると、開発プロセスの一環としてWebサービスの更新、再ビルド、アンデプロイおよび再デプロイを繰り返し実行できます。

Webサービスを実行するには、そのWebサービスを呼び出すクライアントを作成する必要があります。Webサービスを呼び出すJavaクライアント・アプリケーションの作成例については、「WebLogic WebサービスからのWebサービスの呼出し」を参照してください。

サンプルのWSDLファイル

<?xml version="1.0"?>
<definitions
name="TemperatureService"
targetNamespace="http://www.xmethods.net/sd/TemperatureService.wsdl"
xmlns:tns="http://www.xmethods.net/sd/TemperatureService.wsdl"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns="http://schemas.xmlsoap.org/wsdl/" >
<types>
<xsd:schema
targetNamespace="http://www.xmethods.net/sd/TemperatureService.wsdl"
xmlns:xsd="http://www.w3.org/2001/XMLSchema" >
<xsd:element name="getTempRequest">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="zip" type="xsd:string"/>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
<xsd:element name="getTempResponse">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="return" type="xsd:float"/>
</xsd:sequence>
</xsd:complexType>
</xsd:element>
</xsd:schema>
</types>
<message name="getTempRequest">
<part name="parameters" element="tns:getTempRequest"/>
</message>
<message name="getTempResponse">
<part name="parameters" element="tns:getTempResponse"/>
</message>
<portType name="TemperaturePortType">
<operation name="getTemp">
<input message="tns:getTempRequest"/>
<output message="tns:getTempResponse"/>
</operation>
</portType>
<binding name="TemperatureBinding" type="tns:TemperaturePortType">
<soap:binding style="document"
transport="http://schemas.xmlsoap.org/soap/http"/>
<operation name="getTemp">
<soap:operation soapAction=""/>
<input>
<soap:body use="literal"/>
</input>
<output>
<soap:body use="literal"/>
</output>
</operation>
</binding>
<service name="TemperatureService">
<documentation>
Returns current temperature in a given U.S. zipcode
</documentation>
<port name="TemperaturePort" binding="tns:TemperatureBinding">
<soap:address
location="http://localhost:7001/temp/TemperatureService"/>
</port>
</service>
</definitions>

TemperatureService_TemperaturePortImpl Java実装ファイルのサンプル

package examples.webservices.wsdlc;
import javax.jws.WebService;
import javax.xml.ws.BindingType;

/**
* Returns current temperature in a given U.S. zipcode
* This class was generated by the JAX-WS RI.
* JAX-WS RI 2.2.8-b13684
* Generated source version: 2.2
*
*/
@WebService(
portName = "TemperaturePort",
serviceName = "TemperatureService",
targetNamespace="http://www.xmethods.net/sd/TemperatureService.wsdl"
wsdlLocation = "/wsdls/TemperatureService.wsdl",
endpointInterface = "examples.webservices.wsdlc.TemperaturePortType")
@BindingType("http://schemas.xmlsoap.org/wsdl/soap/http")
public class TemperatureService_TemperaturePortImpl implements
TemperaturePortType
{
public TemperatureService_TemperaturePortImpl() { }
/**
*
* @param zip
* @return
*     returns float
*/
public float getTemp(String zip) {
return 1.234f;
}
}

TemperatureServiceのサンプルAntビルド・ファイル

以下のbuild.xmlファイルでは、プロパティを使用してファイルを簡素化しています。

<project default="all">
<!-- set global properties for this build -->
<property name="wls.username" value="weblogic" />
<property name="wls.password" value="weblogic" />
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="wls.server.name" value="myserver" />
<property name="ear.deployed.name" value="wsdlcEar" />
<property name="example-output" value="output" />
<property name="compiledWsdl-dir" value="${example-output}/compiledWsdl" />
<property name="impl-dir" value="${example-output}/impl" />
<property name="ear-dir" value="${example-output}/wsdlcEar" />
<property name="clientclass-dir" value="${example-output}/clientclasses" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="wsdlc"
classname="weblogic.wsee.tools.anttasks.WsdlcTask"/>
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="all"
depends="clean,generate-from-wsdl,build-service,deploy,client" />
<target name="clean" depends="undeploy">
<delete dir="${example-output}"/>
</target>
<target name="generate-from-wsdl">
<wsdlc
srcWsdl="wsdl_files/TemperatureService.wsdl"
destJwsDir="${compiledWsdl-dir}"
destImplDir="${impl-dir}"
packageName="examples.webservices.wsdlc"
type="JAXWS"/>
</target>
<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}">
<jws
file="examples/webservices/wsdlc/TemperatureService_TemperaturePortImpl.java"
compiledWsdl="${compiledWsdl-dir}/TemperatureService_wsdl.jar"
type="JAXWS">
<WLHttpTransport
contextPath="temp" serviceUri="TemperatureService"
portName="TemperaturePort"/>
</jws>
</jwsc>
</target>
<target name="deploy">
<wldeploy action="deploy" name="${ear.deployed.name}"
source="${ear-dir}" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="undeploy">
<wldeploy action="undeploy" name="${ear.deployed.name}"
failonerror="false"
user="${wls.username}" password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/temp/TemperatureService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.wsdlc.client"
type="JAXWS">
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/wsdlc/client/**/*.java"/>
</target>
<target name="run">
<java classname="examples.webservices.wsdlc.client.TemperatureClient"
fork="true" failonerror="true" >
<classpath refid="client.class.path"/>
<arg
line="http://${wls.hostname}:${wls.port}/temp/TemperatureService" />
</java>
</target>
</project>

第III部

基本的なJAX-WS Webサービス・クライアントの開発

第III部では、Java API for XML-based Web Services (JAX-WS)を使用して基本的なWebLogic Webサービス・クライアントを開発する方法について説明します。

ここで説明する内容は次のとおりです。

- 第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」

- 第8章「Webサービス・クライアントの開発」

- 第9章「JAX-WS Webサービス・クライアントの開発例」

7 JAX-WS Webサービス・クライアントを開発するためのロードマップ

この章では、WebLogic Server 12.1.3のJava API for XML Web Services (JAX-WS)用のWebLogic Webサービス・クライアントを開発するためのベスト・プラクティスについて説明します。

表7-1では、各ベスト・プラクティスとその例を示します。ベスト・プラクティスについては、このドキュメント内で後で詳しく説明します。

その他のベスト・プラクティスについては、次の項を参照してください。

- 非同期Webサービス・クライアントの開発の際のベスト・プラクティスについては、第11章「非同期Webサービス・クライアントを開発するためのロードマップ」を参照してください。

- 信頼性のあるWebサービス・クライアントの開発の際のベスト・プラクティスについては、第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

注意:
次の表でクライアント・インスタンスは、ポートまたはディスパッチ・インスタンスです。

表7-1 Webサービス・クライアントを開発するためのロードマップ

ベスト・プラクティス

説明

クライアント・インスタンスの使用と同期させます。

クライアント・インスタンスは必要なときに作成します。長い間保存しないようにしてください。

クライアントIDを含む機能の保管されたリストを使用して、クライアント・インスタンスを作成します。

クライアントIDが含まれるWebサービス・クライアント・インスタンスのすべての機能を定義し、クライアント・インスタンスを作成するたびに異なることがないようにします。例:

_service.getBackendServicePort(_features);

クライアントIDを明示的に定義します。

ClientIdentityFeatureを使用してクライアントIDを明示的に定義します。このクライアントIDを使用して、実行時検証のレポートの目的などで統計情報およびその他の監視情報をグループ化します。詳細は、「クライアントIDの管理」を参照してください。

注意: クライアントIDは明示的に定義することを強くお薦めします。明示的に定義しないと、サーバーによって自動的にクライアントIDが生成されますが、ユーザーにとってわかりにくい場合があります。

処理が完了したら、クライアント・インスタンスを明示的に閉じます。

例:

((java.io.Closeable)port).close();

明示的に閉じないと、クライアント・インスタンスはユーザーがスコープ外になった時点で自動的に閉じられます。

注意: クライアントIDは、コンテナ(WebアプリケーションまたはEJB)が非アクティブ化されるまで、登録済みで可視の状態を維持します。詳細は、「クライアント・アイデンティティのライフサイクル」を参照してください。

次の例では、Webサービス・クライアントを開発するためのベスト・プラクティスを示します。

例7-1 Webサービス・クライアントのベスト・プラクティスの例

import java.io.IOException;
import java.util.*;

import javax.servlet.*;
import javax.xml.ws.*;

import weblogic.jws.jaxws.client.ClientIdentityFeature;

/**
* Example client for invoking a web service.
*/
public class BestPracticeClient
extends GenericServlet {

private BackendServiceService _service;
private WebServiceFeature[] _features;
private ClientIdentityFeature _clientIdFeature;

@Override
public void init()
throws ServletException {

// Create a single instance of a web service as it is expensive to create repeatedly.
if (_service == null) {
_service = new BackendServiceService();
}

// Best Practice: Use a stored list of features, per client ID, to create client instances.
// Define all features for the web service client instance, per client ID, so that they are
// consistent each time the client instance is created. For example:
// _service.getBackendServicePort(_features);

List<WebServiceFeature> features = new ArrayList<WebServiceFeature>();

// Best Practice: Explicitly define the client ID.
// TODO: Maybe allow ClientIdentityFeature to store other features, and
//       then create new client instances simply by passing the
//       ClientIdentityFeature (and the registered features are used).
_clientIdFeature = new ClientIdentityFeature("MyBackendServiceClient");
features.add(_clientIdFeature);

// Set the features used when creating clients with
// the client ID "MyBackendServiceClient". The features are stored in an array to
// reinforce that the list should be treated as immutable.
_features = features.toArray(new WebServiceFeature[features.size()]);
}

@Override
public void service(ServletRequest req, ServletResponse res)
throws ServletException, IOException {

// ... Read the servlet request ...

// Best Practice: Synchronize use of client instances.
// Create a web service client instance to talk to the backend service.
// Note, at this point the client ID is 'registered' and becomes
// visible to monitoring tools such as the Administration Console and WLST.
// The client ID *remains* registered and visible until the container
// (the Web application hosting our servlet) is deactivated (undeployed).
//
// A client ID can be used when creating multiple client instances (port or Dispatch client).
// The client instance should be created with the same set of features each time, and should
// use the same service class and refer to the same port type.
// A given a client ID should be used for a given port type, but not across port types.
// It can be used for both port and Dispatch clients.
BackendService port =
_service.getBackendServicePort(_features);

// Set the endpoint address for BackendService.
((BindingProvider)port).getRequestContext().
put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://localhost:7001/BestPracticeService/BackendService");

// Print out the explicit client ID, and compare it to the client ID
// that would have been generated automatically for the client instance.
showClientIdentity();

// Make the invocation on our real port
String request = "Make a cake";
System.out.println("Invoking DoSomething with request: " + request);
String response = port.doSomething(request);
System.out.println("Got response: " + response);
res.getWriter().write(response);

// Best Practice: Explicitly close client instances when processing is complete.
// If not closed, the client instance will be closed automatically when it goes out of
// scope. Note, this client ID will remain registered and visible until our
// container (Web application) is undeployed.
((java.io.Closeable)port).close();
}

/**
// Print out the client's full ID, which is a combination of
// the client ID provided above and qualifiers from the application and
// Web application that contain the client. Then compare this with the client ID that
// would have been generated for the client instance if not explicitly set.
//
private void showClientIdentity()
throws IOException {

System.out.println("Client Identity is: " + _clientIdFeature.getClientId());

// Create a client instance without explicitly defining the client ID to view the
// client ID that is generated automatically.
ClientIdentityFeature dummyClientIdFeature =
new ClientIdentityFeature(null);
BackendService dummyPort =
_service.getBackendServicePort(dummyClientIdFeature);
System.out.println("Generated Client Identity is: " +
dummyClientIdFeature.getClientId());
// Best Practice: Explicitly close client instances when processing is complete.
// If not closed, the client instance will be closed automatically when it goes out of
// scope. Note, this client ID will remain registered and visible until our
// container (Web application) is undeployed.
((java.io.Closeable)dummyPort).close();
}

@Override
public void destroy() {
}
}

8 Webサービス・クライアントの開発

この章では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスを呼び出すJava EEクライアントの開発方法について説明します。

この章の内容は次のとおりです。

- WebLogic Webサービス・クライアント開発の概要

- Java SEクライアントからのWebサービスの呼出し

- スタンドアロンのJava SEクライアントからのWebサービスの呼出し

- 別のWebLogic WebサービスからのWebサービスの呼出し

- Webサービス・クライアントの構成

- @WebServiceRefアノテーションを使用したWebサービス参照の定義

- クライアントIDの管理

- Webサービス呼出し時のプロキシ・サーバーの使用

- Webサービスを再デプロイする際にクライアント側で考慮すべき事項

- Webサービスおよびクライアントを同一の管理対象サーバーにデプロイする場合のクライアントに関する考慮事項

WebLogic Webサービス・クライアント開発の概要

Webサービスの起動とは、Webサービスを使用するためにクライアント・アプリケーションが実行する操作のことです。

クライアント・アプリケーションには以下の2種類があります。

- Java SE クライアント - 最も単純な形式では、javaコマンドで呼び出すMainパブリック・クラスがあるJavaプログラムです。Java SEクライアントは、WebLogic Server環境(WebLogic Serverクラスパスへのアクセスが可能)内から、またはスタンドアロン・クライアント・アプリケーションとして、呼び出すことができます。

- WebLogic ServerにデプロイされたJava EEコンポーネント - この種のクライアント・アプリケーションでは、EJB、サーブレット、または別のWebサービスなど、WebLogic ServerにデプロイされているJava Platform, Enterprise Edition (Java EE)バージョン5コンポーネント内でWebサービスが実行されます。したがって、WebLogic Serverコンテナの内部で実行されます。

以降の項では、JAX-WS仕様のOracleの実装を使用して、Javaクライアント・アプリケーションからWebサービスを呼び出す方法について説明します。この実装を使用することで、WebLogicおよび非WebLogicにかかわらず任意のアプリケーション・サーバーで実行されているWebサービスを呼び出すことができます。

WebLogic ServerのEXAMPLES_HOME/wl_server/examples/src/examplesディレクトリには、必要に応じてWebLogic Webサービスの作成と呼び出しのサンプルが含まれます(EXAMPLES_HOMEは、WebLogic Serverのコード例が構成されているディレクトリです)。サンプルのビルドおよび実行方法の詳細は、ブラウザでWebページEXAMPLES_HOME/wl_server/docs/index.htmlを開き、「WebLogic Server Examples」→「Examples」→「API」→「Web Services」ノードを開いてください。詳細は、『Oracle WebLogic Serverの理解』のサンプル・アプリケーションおよびサンプル・コードに関する項を参照してください。

詳細は、次を参照してください。

- メッセージ保護されたWebサービスの呼出しの詳細は、『Oracle WebLogic Server WebLogic Webサービスの保護』のクライアント・アプリケーションの更新によるメッセージ保護されたWebサービスの呼出しに関する項を参照してください。

- Webサービス・クライアントの開発に関するベスト・プラクティスについては、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」を参照してください。

- 非同期でWebサービスを呼び出す方法については、第12章「非同期クライアントの開発」を参照してください。

- javax.xml.ws.Service APIを使用して、Webサービス・クライアントがサービス・エンドポイント・インタフェース(SEI)に基づいて実行時に動的にWebサービスを呼び出す(clientgenは使用しない)ことができる動的プロキシ・クライアントを作成する方法については、第27章「動的プロキシ・クライアントの開発」を参照してください。この章では、呼び出す特定のWebサービスに対してServiceインタフェース実装の静的Javaクラスを生成する方法に重点を置いています。

Java SEクライアントからのWebサービスの呼出し

次の表では、Webサービスを呼び出すJava SEアプリケーションを作成する主要な手順をまとめています。

注意:
この項では、次のことを前提としています。

- clientgenまたはwsdlc Antタスクによって生成されたクライアント側アーティファクトを使用してWebサービスを呼び出す場合に、WebLogic Serverクラス全体がCLASSPATHに指定されていること。WebLogic Serverライブラリが使用できない環境で実行されているスタンドアロンJavaアプリケーションのサポートについては、「スタンドアロンのJava SEクライアントからのWebサービスの呼出し」を参照してください。

- 開発環境でのクライアント・アプリケーションのビルドやJavaファイルのコンパイルなどにAntを使用すること、およびWebサービスのクライアント・タスクで更新する必要のあるbuild.xmlファイルがすでに存在すること。開発環境でのAntの使用に関する一般情報は、「基本的なAnt build.xmlファイルの作成」を参照してください。この項で使用しているbuild.xmlファイルの完全な例は、「JavaクライアントのサンプルAntビルド・ファイル」を参照してください。

表8-1 Java SEクライアントからWebサービスを呼び出す手順

#

手順

説明

1

環境を設定します。

コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)コマンドを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2

build.xmlファイルを更新して、Webサービスの呼出しに必要なクライアント側アーティファクトを生成するclientgen Antタスクが実行されるようにします。

「クライアントのアーティファクトを生成するためのclientgen Antタスクの使用」を参照してください。

3

Webサービスに関する情報(その操作のシグネチャ、ポートの名前など)を取得します。

「Webサービスに関する情報の取得」を参照してください。

4

Webサービス操作を呼び出すためのコードを含むクライアント・アプリケーションのJavaコードを記述します。

「Webサービスを呼び出すJavaクライアント・アプリケーション・コードの記述」を参照してください。

5

基本のAntビルド・ファイルbuild.xmlを作成します。

「基本的なAnt build.xmlファイルの作成」を参照してください。

6

Javaクライアント・アプリケーションをコンパイルし、実行します。

「クライアント・アプリケーションのコンパイルと実行」を参照してください。

クライアントのアーティファクトを生成するためのclientgen Antタスクの使用

clientgen WebLogic WebサービスAntタスクは、クライアント・アプリケーションがWebLogic Webサービスと非WebLogic Webサービスの両方の呼出しに使用できるクライアント・アーティファクトを既存のWSDLファイルから生成します。次のようなアーティファクトがあります。

- 呼出しの対象となる特定のWebサービスに対するServiceインタフェース実装のJavaクラス。

- JAXBデータ・バインディング・アーティファクト。

- WSDLファイルで指定されたユーザー定義XMLスキーマ・データ型のJavaクラス。

clientgen Antタスクの詳細(使用可能なすべての属性など)は、『『Oracle WebLogic Server WebLogic Webサービス・リファレンス』』のAntタスク・リファレンスに関する項を参照してください。

次のサンプルのように、build.xmlファイルを更新してclientgen Antタスクに呼出しを追加します。

<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<target name="build-client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
destDir="clientclasses"
packageName="examples.webservices.simple_client"
type="JAXWS"/>
</target>

clientgen WebLogic WebサービスAntタスクを実行するには、その前にこのタスクの完全なJavaクラス名を標準のtaskdef Antタスクを使用して指定する必要があります。

クライアント側アーティファクトの作成に使用するWSDLファイルと、そうしたアーティファクトの生成先ディレクトリを指定するには、clientgen Antタスクのwsdl属性とdestDir属性を含める必要があります。packageName属性は省略できます。省略した場合、clientgenタスクではWSDLのtargetNamespaceに基づくパッケージ名が使用されます。この例ではtypeを指定する必要があります。指定しない場合、JAXRPCがデフォルト値になります。

この例では、パッケージ名はクライアント・アプリケーションと同じパッケージ名examples.webservices.simple_clientに設定されます。パッケージ名をクライアント・アプリケーションとは異なる名前に設定した場合は、適切なクラス・ファイルをインポートする必要があります。たとえば、examples.webservices.complexというパッケージ名にした場合、クライアント・アプリケーションの以下のクラス・ファイルをインポートする必要があります。

import examples.webservices.complex.BasicStruct;
import examples.webservices.complex.ComplexPortType;
import examples.webservices.complex.ComplexService;

注意:
clientgen AntタスクのdestFile属性を使用すると、生成されたJavaファイルを自動的にコンパイルして、すべてのアーティファクトをJARファイルにパッケージ化できます。詳細と例については、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のclientgenに関する項を参照してください。

WSDLファイルで、Webサービス操作の入力パラメータまたは戻り値としてユーザー定義のデータ型が指定されている場合、clientgenはWSDLに定義されたXMLスキーマ・データ型のJava表現であるJavaBeanクラスを自動的に生成します。JavaBeanクラスは、destDirディレクトリに生成されます。

この手順で説明されている追加のターゲット(cleanなど)を含む、完全なサンプルbuild.xmlファイルについては、「JavaクライアントのサンプルAntビルド・ファイル」を参照してください。

clientgen Antタスクを他のサポートAntタスクと一緒に実行するには、コマンド・ラインでbuild-clientターゲットを指定します。

prompt> ant build-client

clientclassesディレクトリで、clientgen Antタスクによって生成されたファイルやアーティファクトを確認します。

Webサービスに関する情報の取得

操作を呼び出すJavaクライアント・アプリケーション・コードの記述に先立って、Webサービスの名前と操作のシグネチャを知る必要があります。この情報を調べるには様々な方法があります。

一番よいのは、clientgen Antタスクを使用してWebサービス固有のServiceファイルを生成し、生成された*.javaファイルを調べる方法です。destDir属性で指定したディレクトリ内のpackageName属性の値に対応したサブディレクトリに生成されます。packageName属性が指定されていない場合、WSDLのtargetNamespaceに基づくパッケージに対応したサブディレクトリに生成されます。

- ServiceName.javaソース・ファイルには、Webサービスのポートを取得するためのgetPortName()メソッドが含まれており、ServiceNameはWebサービス名、PortNameはポート名を意味します。WebサービスがJWSファイルで実装されている場合、Webサービス名は@WebService JWSアノテーションのserviceName属性の値となり、ポート名はjwsc Antタスクの<jws>要素の子要素<WLHttpTransport>のportName属性の値となります。

- PortType.javaファイルには、Webサービスのパブリック操作に対応するメソッド・シグネチャが含まれており、PortTypeはWebサービスのポートの種類を表します。WebサービスがJWSファイルで実装されている場合、ポートの種類は@WebService JWSアノテーションのname属性の値となります。

Webサービスの実際のWSDLを調べることもできます。デプロイされているWebLogic WebサービスのWSDLの詳細は、「WebサービスのWSDLの参照」を参照してください。Webサービス名は、次のTraderService WSDLの引用に示すように、<service>要素内にあります。

<service name="TraderService">
<port name="TraderServicePort"
binding="tns:TraderServiceSoapBinding">
...
</port>
</service>

このWebサービス用に定義されている操作は、対応する<binding>要素の下に記述されています。たとえば次のWSDLの抜粋は、TraderService Webサービスにbuyとsellの2つの操作があることを示しています(わかりやすくするため、WSDLの関連部分のみを記載しています)。

<binding name="TraderServiceSoapBinding" ...>
...
<operation name="sell">
...
</operation>
<operation name="buy">
</operation>
</binding>

Webサービスを呼び出すJavaクライアント・アプリケーション・コードの記述

次のサンプル・コードでは、JavaアプリケーションがWebサービス操作を呼び出しています。アプリケーションは、標準JAX-WS APIコードと、clientgenによって生成されたServiceインタフェースのWebサービス固有の実装を使用して、Webサービスの操作を呼び出します。

このサンプルでは、ユーザー定義のデータ型(examples.webservices.simple_client.BasicStruct)を入力パラメータおよび戻り値として使用する操作を呼び出す方法も示します。clientgen Antタスクによって、このユーザー定義のデータ型のJavaコードが自動的に生成されます。

<clientgen> packageName属性はクライアント・アプリケーションと同じパッケージ名に設定されているため、<clientgen>生成ファイルをインポートする必要はありません。

package examples.webservices.simple_client;
/**
* This is a simple Java application that invokes the
* the echoComplexType operation of the ComplexService web service.
*/
public class Main {
public static void main(String[] args) {
ComplexService test = new ComplexService();
ComplexPortType port = test.getComplexPortTypePort();
BasicStruct in = new BasicStruct();
in.setIntValue(999);
in.setStringValue("Hello Struct");
BasicStruct result = port.echoComplexType(in);
System.out.println("echoComplexType called. Result: " + result.getIntValue() + ", " + result.getStringValue());
}
}

上記の例で注目すべき点は以下のとおりです。

- 次のコードは、ComplexPortTypeスタブを作成する方法を示します。

ComplexService test = new ComplexService(),
ComplexPortType port = test.getComplexPortTypePort();

ComplexServiceクラスはJAX-WS Serviceインタフェースを実装します。getComplexServicePortTypePort()メソッドは、ComplexPortTypeスタブ実装のインスタンスを返すために使用します。

- 次のコードは、ComplexService WebサービスのechoComplexType操作を呼び出す方法を示します。

BasicStruct result = port.echoComplexType(in);

echoComplexType操作は、BasicStructというユーザー定義データ型を返します。

クライアント・アプリケーションのコンパイルと実行

すべてのJavaファイル(クライアント・アプリケーションおよびclientgenによって生成されたファイルの両方)をクラス・ファイルにコンパイルするには、build.xmlファイルのbuild-clientターゲットにjavacタスクを追加します。該当箇所を次のサンプルに太字で示します。

<target name="build-client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
destDir="clientclasses"
packageName="examples.webservices.simple_client"
type="JAXWS"/>
<javac
srcdir="clientclasses"
destdir="clientclasses"
includes="**/*.java"/>
<javac
srcdir="src"
destdir="clientclasses"
includes="examples/webservices/simple_client/*.java"/>
</target>

この例では、1番目のjavacタスクでclientgenによって生成されたclientclassesディレクトリ内のJavaファイルをコンパイルし、2番目のjavacタスクでカレント・ディレクトリのexamples/webservices/simple_clientサブディレクトリ(Javaクライアント・アプリケーションのソースの場所と想定されるディレクトリ)内にあるJavaファイルをコンパイルしています。

この例では、clientgenによって生成されたJavaソース・ファイルとコンパイル後のクラスが同じディレクトリ(clientclasses)に格納されます。プロトタイピングの段階ではこれで十分ですが、多くの場合はソース・コード(生成されたコードも含む)とコンパイルされたクラスを別々のディレクトリに格納するのがベスト・プラクティスです。これを行うには、両方のjavacタスクのdestdirに、srcdirディレクトリとは異なるディレクトリを設定します。クライアント・アプリケーションを実行するには、javaタスクの呼出しを含むbuild.xmlにrunターゲットを追加します。次に例を示します。

<path id="client.class.path">
<pathelement path="clientclasses"/>
<pathelement path="${java.class.path}"/>
</path>
<target name="run" >
<java
fork="true"
classname="examples.webServices.simple_client.Main"
failonerror="true" >
<classpath refid="client.class.path"/>
</target>

pathタスクは、CLASSPATHにclientclassesディレクトリを追加します。runターゲットはMainアプリケーションを呼び出し、デプロイされたWebサービスのURLを1つの引数として渡します。

この手順で説明されている追加のターゲット(cleanなど)を含む、完全なサンプルbuild.xmlファイルについては、「JavaクライアントのサンプルAntビルド・ファイル」を参照してください。

アーティファクトを再生成してクラスに再コンパイルするためにbuild-clientターゲットを再実行してから、runターゲットを実行してechoStruct操作を呼び出します。

prompt> ant build-client run

build.xmlファイルのbuild-clientおよびrunターゲットを使用して、開発プロセスの一環としてJavaクライアント・アプリケーションを繰返し更新、再ビルド、および実行できます。

JavaクライアントのサンプルAntビルド・ファイル

次の例では、Javaクライアントを生成およびコンパイルするための完全なbuild.xmlファイルを示します。太字のセクションについては、「クライアントのアーティファクトを生成するためのclientgen Antタスクの使用」および「クライアント・アプリケーションのコンパイルと実行」を参照してください。

<project name="webservices-simple_client" default="all">
<!-- set global properties for this build -->
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="example-output" value="output" />
<property name="clientclass-dir" value="${example-output}/clientclass" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<target name="clean" >
<delete dir="${clientclass-dir}"/>
</target>
<target name="all" depends="clean,build-client,run" />
<target name="build-client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.simple_client"
type="JAXWS"/>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/simple_client/*.java"/>
</target>
<target name="run" >
<java fork="true"
classname="examples.webservices.simple_client.Main"
failonerror="true" >
<classpath refid="client.class.path"/>
</java>
</target>
</project>

スタンドアロンのJava SEクライアントからのWebサービスの呼出し

Java SEクライアントからWebサービスを呼び出す際、clientgenまたはwsdlc Antタスクによって生成されたクライアント側アーティファクトを使用してWebサービスを呼び出す場合に、WebLogic Serverクラス全体がCLASSPATHに指定されていることが前提となります。ただし、WebLogic Serverがローカルにインストールされていない場合でも、スタンドアロンのWebLogic Webサービス・クライアントJARファイルのいずれかを使用することで、Webサービスを呼び出すことができます。

表8-2では、このインストールで使用可能なWebサービス・クライアントJARファイルについて説明します。

表8-2 スタンドアロンのWebサービス・クライアントJARファイル

JARファイル

場所

説明

com.oracle.webservices.wls.jaxws-wlswss-client.jar

ORACLE_HOME/wlserver/modules/clients/

次のような基本的なJAX-WSクライアント側の機能をサポートしています。

- clientgen Antタスクの双方によって作成されるクライアント側アーティファクトの使用

- SOAPメッセージの処理

- Webサービスの信頼性のあるメッセージング、WSアドレッシング、非同期リクエスト/レスポンス、MTOMなど、高度な機能の使用

- WS-Securityの使用

- クライアント側のSOAPメッセージ・ハンドラの使用

- JAX-WS WebサービスとJAX-RPC Webサービスの両方の呼出し

- SSLの使用

スタンドアロン・クライアントJARは、次の高度な機能を使用するWebサービスの呼出しはサポートしていません。

- SOAP Over JMSトランスポート

- 会話

- バッファリング

com.oracle.webservices.wls.jaxws-owsm-client_12.1.3.jar

ORACLE_HOME/oracle_common/modules/clients/

com.oracle.webservices.wlsjaxws-client_12.1.2.jar (前述)と同様の機能、およびOracle Web Services Manager (OWSM)セキュリティ・ポリシー(『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』を参照)をサポートします。

com.oracle.webservices.fmw.client_12.1.3.jar

ORACLE_HOME/oracle_common/modules/clients/

WS-Secure Conversationセキュリティ(『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のセキュアな会話の構成に関する項を参照)をサポートします。

クライアント・アプリケーションでスタンドアロンのWebサービス・クライアントJARファイルを使用するには、次の手順を実行します。

1. Oracle JDeveloperなど任意のIDEを使用して、Java SEクライアントを作成します。詳細は、『Oracle JDeveloperによるアプリケーションの開発』のWebサービスおよびクライアントの開発と保護に関する項を参照してください。

2. 表8-2に定義した必要なJARファイルを、WebLogic Serverをホストしているコンピュータからスタンドアロン・クライアント・コンピュータの適切なディレクトリにコピーします。
たとえば、クライアント・アプリケーションで使用している他のクラスが格納されているディレクトリをコピー先にします。

3. JARファイルをCLASSPATHに追加します。

注意:
スタンドアロンのクライアントJARファイルによりサブセットが使用されるため、Antクラスが含まれるJARファイル(ant.jar)が、確実にCLASSPATHに格納されるようにしてください。このJARファイルは通常、Antディストリビューションのlibディレクトリ内にあります。

4. Oracle Web Services Manager (OWSM)ポリシーの環境を構成します。この手順はオプションです。OWSMセキュリティ・ポリシーをWebサービス・クライアントにアタッチしている場合にのみ必須となります。
必要な構成手順は、アタッチされているポリシーのタイプによって異なります。次に例を示します。その他の構成要件については、『Oracle Platform Security Servicesによるアプリケーションの保護』のOPSSを使用するためのJava SEアプリケーションの構成に関する項を参照してください。

例: 基本認証

たとえば、oracle/wss_http_token_client_policyセキュリティ・ポリシーを使用して基本認証をサポートするには、次の手順を実行します。

1. jps-config-jse.xmlおよびaudit-store.xmlファイルを、domain_home/config/fmwconfigディレクトリ(domain_homeはドメインの名前および場所)から、Webサービス・クライアントがアクセス可能な場所にコピーします。

2. 手順2でファイルをコピーした場所に、oracle.wsm.securityというマップとクライアント・アプリケーションが使用する資格証明キーの名前(weblogic-csf-keyなど)を定義するウォレット(cwallet.sso)を作成します。
ファイルcwallet.ssoの場所は、構成ファイルjps-config-jse.xmlに、要素<serviceInstanceを使用して指定します。詳細は、『Oracle Platform Security Servicesによるアプリケーションの保護』のウォレットベースの資格証明ストアの使用に関する項を参照してください。

3. Javaコマンド・ラインで、手順1でコピーしたJPS構成ファイルを定義する次のプロパティを渡します。

-Doracle.security.jps.config=<pathToConfigFile>

詳細は、『Oracle Platform Security Servicesによるアプリケーションの保護』のシナリオ3: Java SEアプリケーションの保護に関する項を参照してください。

例: SSL

たとえば、SSLポリシーをサポートするには、次の手順を実行します。

1. jps-config-jse.xmlおよびaudit-store.xmlファイルを、domain_home/config/fmwconfigディレクトリ(domain_homeはドメインの名前および場所)から、Webサービス・クライアントがアクセス可能な場所にコピーします。

2. Javaコマンド・ラインで、次のプロパティを渡します: 手順1でコピーしたJPS構成ファイルを定義します:
手順1でコピーしたJPS構成ファイルを定義します。

-Doracle.security.jps.config=<pathToConfigFile>

詳細は、『Oracle Platform Security Servicesによるアプリケーションの保護』のシナリオ3: Java SEアプリケーションの保護に関する項を参照してください。

信頼済証明書が格納される信頼ストアを定義します。

-Djavax.net.ssl.trustStore=<trustStore>

詳細は、『Oracle Platform Security Servicesによるアプリケーションの保護』のLDAPへの一方向SSL接続の設定に関する項にある、Java SEアプリケーションの場合のWebLogic Serverの設定を参照してください。

信頼ストアのパスワードを定義します。

-Djavax.net.ssl.trustStorePassword=<password>

別のWebLogic WebサービスからのWebサービスの呼出し

別のWebLogic Webサービスなど、Java EEクライアントからのWebサービスの呼出しは、「Java SEクライアントからのWebサービスの呼出し」で説明している、Java SEアプリケーションからのWebサービスの呼出しに似ていますが、次の点が異なります。

- 呼び出されるWebサービスのJAX-WS Serviceインタフェースを生成するclientgen Antタスクを使用するかわりに、呼び出す側のWebサービスをコンパイルするjwsc Antタスクの内部で、<jws>要素の<clientgen>子要素を使用します。一方、他のWebサービスを呼び出すJWSファイルでは、ServiceおよびPortTypeインスタンスの取得に同じ標準JAX-WS APIを使用して、Webサービス操作を呼び出します。

- Webサービスに対する参照の定義に@WebServiceRefアノテーションを使用できます。「Webサービスを呼び出すサンプルJWSファイル」を参照してください。

この項では、Webサービス(特に別のWebサービス)をJava EEコンポーネント内のクライアントから呼び出す場合とJava SEクライアントから呼び出す場合の違いについて説明します。開発環境でのクライアント・アプリケーションのビルドやJavaファイルのコンパイルなどにAntを使用していること、および別のWebサービスを呼び出すために更新が必要なWebサービスを構築するbuild.xmlファイルが、すでに存在することが前提となっています。

クライアントWebサービスをビルドするbuild.xmlファイルに加える必要のある変更は次のとおりです(このクライアントWebサービスが別のWebサービスを呼び出すことになります)。build.xmlファイルの完全なサンプルについては、「Webサービス・クライアントのサンプルbuild.xmlファイル」を参照してください。

- JWSファイル(別のWebサービスを呼び出すWebサービスを実装しているもの)を指定する<jws>要素に、<clientgen>子要素が追加されます。呼び出されるWebサービスのWSDLに、必要なwsdl属性を設定します。JAX-WSクライアント・スタブの生成先とするパッケージに、必要なpackageName属性を設定します。

クライアントWebサービスを実装するJWSファイルに加える必要のある変更は次のとおりです。JWSファイルの完全なサンプルについては、「Webサービスを呼び出すサンプルJWSファイル」を参照してください。

- jwsc Antタスクの<clientgen>子要素で生成される一連のファイルがインポートされます。これらのファイルには、呼び出されるWebサービスの操作でパラメータまたは戻り値として使用するユーザー定義データ型のJava表現のみでなく、呼び出されるWebサービスのJAX-WS Serviceインタフェースも含まれます。

注意:
<clientgen>のpackageName属性で設定されているパッケージ名が、クライアント・アプリケーションと同じパッケージ名である場合、<clientgen>生成ファイルをインポートする必要はありません。

- ServiceおよびPortTypeインタフェース実装を取得して、通常どおりポート上で操作を呼び出します。詳細は、「Webサービスを呼び出すJavaクライアント・アプリケーション・コードの記述」を参照してください。

Webサービス・クライアントのサンプルbuild.xmlファイル

次のサンプルbuild.xmlファイルでは、別のWebサービスを呼び出すWebサービスを作成する方法を示します。別のWebサービスを呼び出さない単純なWebサービスをビルドするためのbuild.xmlと異なっている部分は、太字で示されています。

この場合のbuild-serviceターゲットは、単純なWebサービスをビルドするターゲットとよく似ています。唯一の違いは、呼び出すWebサービスをビルドするjwsc Antタスクに<jws>要素の<clientgen>子要素も含まれるという点で、これによってjwscでは必要なJAX-WSクライアント・スタブも生成されるようになります。

<project name="webservices-service_to_service" default="all">
<!-- set global properties for this build -->
<property name="wls.username" value="weblogic" />
<property name="wls.password" value="weblogic" />
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="wls.server.name" value="myserver" />
<property name="ear.deployed.name" value="ClientServiceEar" />
<property name="example-output" value="output" />
<property name="ear-dir" value="${example-output}/ClientServiceEar" />
<property name="clientclass-dir" value="${example-output}/clientclasses" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="all" depends="clean,build-service,deploy,client" />
<target name="clean" depends="undeploy">
<delete dir="${example-output}"/>
</target>
<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}" >
<jws
file="examples/webservices/service_to_service/ClientServiceImpl.java"
type="JAXWS">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
packageName="examples.webservices.complex" />
</jws>
</jwsc>
</target>
<target name="deploy">
<wldeploy action="deploy" name="${ear.deployed.name}"
source="${ear-dir}" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="undeploy">
<wldeploy action="undeploy" name="${ear.deployed.name}"
failonerror="false"
user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/ClientService/ClientService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.service_to_service.client"
type="JAXWS"/>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/service_to_service/client/**/*.java"/>
</target>
<target name="run">
<java classname="examples.webservices.service_to_service.client.Main"
fork="true"
failonerror="true" >
<classpath refid="client.class.path"/>
</java>
</target>
</project>

Webサービスを呼び出すサンプルJWSファイル

次に示すサンプルJWSファイル(ClientServiceImpl.java)は、ClientServiceというWebサービスを実装しており、このWebサービスに含まれている操作がComplexServiceというWebサービスのechoComplexType操作を呼び出します。この操作では、パラメータとしても戻り値としてもユーザー定義データ型(BasicStruct)を使用します。該当するコードを太字で示し、例の後で説明を加えます。

package examples.webservices.service_to_service;

import javax.jws.WebService;
import javax.jws.WebMethod;
import javax.xml.ws.WebServiceRef;

// Import the BasicStruct data type, generated by clientgen and used
// by the ComplexService Web Service
import examples.webservices.complex.BasicStruct;

// Import the JAX-WS stubs generated by clientgen for invoking
// the ComplexService web service.
import examples.webservices.complex.ComplexPortType;
import examples.webservices.complex.ComplexService;

@WebService(name="ClientPortType", serviceName="ClientService",
targetNamespace="http://examples.org")
public class ClientServiceImpl {
// Use the @WebServiceRef annotation to define a reference to a web service.
@WebServiceRef()
ComplexService test;

@WebMethod()
public String callComplexService(BasicStruct input, String serviceUrl)
{
// Create a port stub to invoke ComplexService
ComplexPortType port = test.getComplexPortTypePort();

// Invoke the echoComplexType operation of ComplexService
BasicStruct result = port.echoComplexType(input);
System.out.println("Invoked ComplexPortType.echoComplexType." );
return "Invoke went okay!  Here's the result: '" + result.getIntValue() +
",  " + result.getStringValue() + "'";
}
}

別のWebサービスを呼び出すJWSファイルをプログラミングする際は、次のガイドラインに従います。ガイドラインのサンプル・コードは、上述のサンプル内では太字で示されています。

- 呼び出されるWebサービスで使用されるユーザー定義データ型をインポートします。このサンプルでは、ComplexServiceでBasicStruct JavaBeanを使用しています。

import examples.webservices.complex.BasicStruct;

- ComplexService WebサービスのJAX-WSインタフェースをインポートします。このスタブは、<jws>の<cliengen>子要素によって生成されます。

import examples.webservices.complex.ComplexPortType;
import examples.webservices.complex.ComplexService;

- @WebServiceRefアノテーションを使用して、Webサービスへの参照およびそのインジェクション・ターゲットを定義します。

@WebServiceRef()
ComplexService service;

@WebServiceRefの詳細は、「@WebServiceRefアノテーションを使用したWebサービス参照の定義」を参照してください。

または、次に示すように、ComplexService Webサービスへのプロキシ・スタブを作成できます。

ComplexService service = new ComplexService();

- Webサービス参照でgetComplexPortTypePort()操作を呼び出すことによって、ComplexPortTypeスタブ実装のインスタンスを戻します。

ComplexPortType port = service.getComplexPortTypePort();

- ComplexServiceのechoComplexType操作を、直前にインスタンス化したポートを使用して呼び出します。

BasicStruct result = port.echoComplexType(input);

Webサービス・クライアントの構成

デフォルトでは、Webサービス・クライアントではサーバーに対して定義されているWebサービス構成を使用します。次のメソッドのいずれかを使用してWebサービス・クライアントが使用する構成設定をオーバーライドできます。

- 該当する場合、管理またはWLSTを使用。クライアントで構成可能なのはWebサービス機能のサブセットのみです。

- @WebServiceRefアノテーションを使用してWebサービスのクライアントを指定のWebサービス参照に対して定義する構成に関連付けます。Webサービスの参照構成はWebコンテナではweblogic.xmlに定義され、EJBコンテナではweblogic-ejb-jar.xmlで定義されます。@WebServiceRefアノテーションの詳細は、「@WebServiceRefアノテーションを使用したWebサービス参照を定義」を参照してください。

- Webサービスの信頼性のあるメッセージング・クライアントを作成する場合は、WsrmClientInitFeatureを使用。詳細は、「Webサービス・クライアントでの信頼性のあるメッセージングの構成」を参照してください。

@WebServiceRefアノテーションを使用したWebサービス参照の定義

@WebServiceRefアノテーションを使用すると、Webサービスへの参照を定義し、クライアント・インスタンスにWebサービスの構成をアタッチできます。

たとえば、次のコードの抜粋では、@WebServiceRefを使用して、クライアントのWebサービス・インスタンスにReliableEchoServiceの構成をアタッチします。後で作成および初期化されるポートは、Webアプリケーションのweblogic.xmlのReliableEchoServiceサービス参照用に定義されているプロパティを使用します。

package wsrm_jaxws.example;
import java.xml.ws.WebService;
import java.xml.ws.WebServiceRef;
import wsrm_jaxws.example.client_service.*;
import wsrm_jaxws.example.client_service.EchoResponse;
...
@WebService
public class ClientServiceImpl {

@WebServiceRef(name="MyServiceRef")
private ReliableEchoService service;
private ReliableEchoPortType port = null;

@PostConstruct
public void initPort() {
port = service.getReliableEchoPort();
...
}
}

例8-1にWebサービス参照の記述を含むweblogic.xmlファイルの例を示します。この例に示されている信頼性のあるメッセージングのプロパティについては、「信頼性のあるメッセージングの構成」を参照してください。

例8-1 Webサービス参照の記述を含むweblogic.xmlのサンプル・ファイル

<?xml version='1.0' encoding='UTF-8'?>
<weblogic-web-app xmlns="http://xmlns.oracle.com/weblogic/weblogic-web-app">
<service-reference-description>
<!-- Any name you want, but use this same name on
@WebServiceRef(name=<my name>). This anno goes on the service
field in your client container -->
<service-ref-name>MyServiceRef</service-ref-name>
<!-- Use / and any path within the web app to get a local WSDL, or
use a resource name as defined by the Java ClassLoader, or use an
absolute/external URL you can guarantee is deployed when this web
app deploys -->
<wsdl-url>/WEB-INF/wsdls/ReliableEcho.wsdl</wsdl-url>
<!-- One or more port-infos, one for each type of port/stub you'll create
in your JWS -->
<port-info>
<!-- The local name of wsdl:port (not portType). The Java type for this
port, when created from the @WebServiceRef JWS field, will contain,
in RequestContext, the props you define below -->
<port-name>ReliableEchoPort</port-name>

<!-- Any prop name/value pairs you want to show up on you service stub
The Java type for this port, when created from the @WebServiceRef JWS field,
will contain, in RequestContext, the stub-props you define below -->

<!-- RM Source Properties -->

<stub-property>
<name>weblogic.wsee.wsrm.BaseRetransmissionInterval</name>
<value>PT30S</value>
</stub-property>

<stub-property>
<name>weblogic.wsee.wsrm.RetransmissionExponentialBackoff</name>
<value>true</value>
</stub-property>

<!-- RM Destination Properties -->

<stub-property>
<name>weblogic.wsee.wsrm.RetryCount</name>
<value>5</value>
</stub-property>

<stub-property>
<name>weblogic.wsee.wsrm.RetryDelay</name>
<value>PT30S</value>
</stub-property>

<stub-property>
<name>weblogic.wsee.wsrm.AcknowledgementInterval</name>
<value>PT5S</value>
</stub-property>

<stub-property>
<name>weblogic.wsee.wsrm.NonBufferedDestination</name>
<value>true</value>
</stub-property>

<!-- RM Source *or* Destination Properties -->

<stub-property>
<name>weblogic.wsee.wsrm.InactivityTimeout</name>
<value>PT5M</value>
</stub-property>

<stub-property>
<name>weblogic.wsee.wsrm.SequenceExpiration</name>
<value>PT10M</value>
</stub-property>

</port-info>

</service-reference-description>
<wl-dispatch-policy>weblogic.wsee.mdb.DispatchPolicy</wl-dispatch-policy>
</weblogic-web-app>

クライアントIDの管理

Webサービスを使用すると、クライアント・アイデンティティ(クライアントID)として表される意味のある名前をクライアントに割り当てることができます。このクライアントIDを使用して、実行時検証のレポートの目的などで統計情報およびその他の監視情報をグループ化します。

サーバー上のクライアント(WebLogic Serverインスタンス内のコンテナで実行されるクライアント)では、次のいずれかの方法でクライアントIDを生成できます。

- Webサービス・ポートへの接続を初期化する場合はクライアントで実行。これは、推奨アプローチです。「ポート初期化時のクライアントIDの定義」を参照してください。

- サーバーで実行、その後クライアントで検出。クライアント「サーバー生成のクライアントIDへのアクセス」を参照してください。

注意:
省略可能ですが、クライアントIDを明示的に定義することをお薦めします。

weblogic.wsee.jaxws.persistence.ClientIdentityFeatureクライアント機能を使用すると、Webサービス・クライアントがWebサービスのクライアントIDを設定およびアクセスできます。次の表では、ClientIdentityFeatureメソッドをまとめます。

表8-3 クライアントIDの設定およびアクセスのためのClientIdentityFeatureメソッド

メソッド

説明

getClientID()

Webサービス・ポートで現在定義されているクライアントIDを取得します。

setClientID()

Webサービス・ポートのクライアントIDを設定します。

また、ClientIdentityFeatureオブジェクトをインスタンス化する場合は、クライアントIDを引数として渡すことにより、クライアントIDを設定できます。例:

ClientIdentityFeature clientIDFeature = new
ClientIdentityFeature("MyBackendServiceAsyncClient");

dispose()

クライアントIDを破棄します。

クライアントIDを明示的に破棄される場合、クライアントIDを使用するクライアント・インスタンスのコンテナが無効化されるとき(ホストWebアプリケーションまたはEJBが無効化される場合など)に実行されます。詳細は、「クライアント・アイデンティティのライフサイクル」を参照してください。

次の項は、クライアントIDを管理するためのメソッドを説明します。

- ポート初期化時のクライアントIDの定義

- サーバー生成のクライアントIDのアクセス

- クライアントIDのライフサイクル

ポート初期化時のクライアントIDの定義

クライアントIDを提供するには、初期化時にクライアントIDを含むClientIdentityFeatureのインスタンスをWebサービス・ポートに渡すことができます。

クライアントIDは、クライアントを含むWebアプリケーションまたはEJB内で一意である必要があります。クライアントIDがビジネスの目的を適宜反映していることをお薦めします。クライアントIDが必ず一意であるようにするため、含む側のサーバー、アプリケーション、コンポーネント(WebアプリケーションまたはEJB)の名前をクライアントIDの前に付けます。

注意:
クライアントIDの選択時は注意する必要があります。既存のクライアント・インスタンスと同じクライアントIDを使用してクライアント・インスタンスを作成する場合、2つのクライアント・インスタンスが同じインスタンスとして処理されます。例外がスローされ重複していることをアラートします。

次の例に、クライアントIDを指定するこのメソッドを示します。次の示すように、すべての処理が完了したら、クライアント・インスタンスを閉じることをお薦めします。

この例は、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」からの抜粋です。

例8-2 ポート初期化時のクライアントIDの指定例

import javax.servlet.*;
import javax.xml.ws.*;
import weblogic.jws.jaxws.client.ClientIdentityFeature;
. . .
public class BestPracticeAsyncClient
extends GenericServlet {
...
private BackendServiceService _service;
...
// Client ID
ClientIdentityFeature clientIdFeature =
new ClientIdentityFeature("MyBackendServiceAsyncClient");
features.add(clientIdFeature);
...
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendService port = _service.getBackendServicePort(_features);
...
((java.io.Closeable)_port).close();
}
}

サーバー生成クライアントIDへのアクセス

注意:
この項での説明に従って、クライアントIDが一意であるようにするため、サーバー生成のバージョンが長く読みにくくなる場合があります。クライアントIDが読みづらい形式で表示されるように保証するため、「ポート初期化時のクライアントIDの定義」の説明に従ってポート初期化時にクライアントIDを定義することをお薦めします。

サーバーが自動生成するクライアントIDでは次の形式を使用します。

applicationname[_applicationversion]:componentname:uniqueID

説明:

- applicationname - クライアントをホストするアプリケーションの名前。

- applicationversion - アプリケーションのバージョン。同じアプリケーションの複数のバーションを同時に実行する場合にのみ使用します。

- componentnam - クライアントをホストするコンポーネント(WebアプリケーションまたはEJB)の名前。

- uniqueID - クライアント・インスタンスが作成される場合に使用可能な情報に基づいて算出されます。uniqueIDは次のいずれか(使用可能な方)を選択することで作成されます。

- Webサービス参照名。@WebServiceRefアノテーションにより定義されます。

- [portNamespaceURI:portLocalName][:][endpointAddress] - ポート名、エンドポイント・アドレスまたは両方(コロンで区切ります)。

- ポートクラスの単純な名前。

また、次の情報(可能な場合)は、次に示す順序でコロン(:)で区切り、uniqueIDに連結することができます。

- WSDLの場所(マイナス記号 ?wsdl)

- クライアント・インスタンスの作成に使用する機能。機能のクラス名で表し、ダッシュ(-)で区切ります。

たとえば、Webサービス・クライアントに関連付けられている次の情報を使用してWebサービス・クライアントをデプロイするとします。

- アプリケーション名: example

- コンポーネント: BestPracticeClientと呼ばれるWebアプリケーション

- ポート名: http://example/BackendServicePort

- ポート・クラス: BackendService

- WSDL: jar:file:/C:/example/BackendService.war!/WEB-INF/BackendServiceService.wsdl

サーバー生成クライアントIDは次のようになります。

example:BestPracticeClient:http://example/:BackendServicePort:jar:file:/C:/example/BackendService.war!/WEB-INF/BackendServiceService.wsdl:AsyncClientTransportFeature()-ClientIdentityFeature

コードを実行するたびに、同一の包含階層内にあることを前提として、同一のクライアントIDが生成されます。これにより、サーバー仮想マシンのインスタンス全体で使用できる安定したクライアントIDを提供し、サーバーの再起動後でも非同期レスポンスをクライアントに配信できます。

注意:
クライアント・コードの複数の場所から特定のクライアントIDを使用できますが、クライアントIDの他の場所で使用されている方法と同じ方法(同じ機能、サービスなど)でクライアントIDを使用するポート/ディスパッチ・インスタンスの初期化時に注意する必要があります。
クライアント・インスタンス(ポートまたはディスパッチ)の初期化における推奨アプローチのベスト・プラクティスは、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」を参照してください。

次の例に、サーバー生成のクライアントIDにアクセスする方法を示します。この例は、「Webサービス・クライアントを開発するためのロードマップ」からの抜粋です。

例8-3 サーバー生成クライアントIDへのアクセス

...
// Create a port without explicitly defining the client ID to view the client ID that is
// generated automatically.
ClientIdentityFeature dummyClientIdFeature = new ClientIdentityFeature(null);
BackendService dummyPort = _service.getBackendServicePort(dummyClientIdFeature);
System.out.println("Generated Client Identity is: " + dummyClientIdFeature.getClientId());

// Best Practice: Explicitly close client instances when processing is complete.
// If not closed, the port will be closed automatically when it goes out of scope.
// Note, this client ID will remain registered and visible until our
// container (Web application) is undeployed.
((java.io.Closeable)dummyPort).close();

クライアントIDのライフサイクル

クライアントIDを使用して最初のクライアント・インスタンス(ポートまたはディスパッチ・インスタンス)が作成されるときに、WebサービスのランタイムでクライアントIDが登録されます。また、クライアント・インスタンスに関連付けられている非同期レスポンスのエンドポイントも登録されているクライアントIDで追跡されます。

クライアントIDは次のいずれかが発生するまで登録が維持されます。

- 表8-3に示すように、クライアントIDは、ClientIdentityFeatureでdispose()メソッドを使用して明示的に公開します。

- クライアントIDを使用するクライアント・インスタンスのコンテナが無効化されます(ホストWebアプリケーションまたはEJBが無効化される場合など)。

Webサービス呼出し時のプロキシ・サーバーの使用

プロキシ・サーバーを使用すると、クライアント・アプリケーションから、呼び出されるWebサービスをホストするアプリケーション・サーバー(WebLogic、非WebLogicいずれでも)へのリクエストをプロキシできます。通常、プロキシ・サーバーは、アプリケーション・サーバーがファイアウォールの内側にある場合に使用します。Javaシステム・プロパティを使用してクライアント・アプリケーションにプロキシ・サーバーを指定できます。クライアント・アプリケーションでプロキシ・サーバーを指定する方法には、WebLogic ClientProxyFeature APIでプログラム的に行う方法と、システム・プロパティを使用する方法の2つがあります。

ClientProxyFeature APIを使用したプロキシ・サーバーの指定

weblogic.wsee.jaxws.proxy.ClientProxyFeature APIを使用してWebサービスの呼出しをプロキシするプロキシ・サーバーの詳細を、Javaクライアント・アプリケーション自体にプログラムで指定できます。ClientProxyFeature APIの詳細は、Oracle WebLogic Server Java APIリファレンスを参照してください。

JVMレベルに定義されている設定は、「システム・プロパティを使用したプロキシ・サーバーの指定」に記載されているように、ClientProxyFeatureで定義されたプロキシ・サーバー設定によってオーバーライドされます。

注意:
ClientProxyFeatureは、WebLogic HTTP over SSLのポートを構成します。WebLogic ServerにはSSLを構成することをお薦めします。詳細は、『Oracle WebLogic Serverセキュリティの管理』のSSLの構成に関する項を参照してください。
ClientProxyFeature setUseSunHttpHandlerメソッドでは、WebLogic Serverは接続リクエストごとにSun HTTP実装を使用することになります。かわりにWebLogic Server起動構成オプション-DUseSunHttpHandler=trueを使用できます。これはWebLogic Serverインスタンスの設定を適用します。

次の例で示すように、ClientProxyFeatureを使用してプロキシ・サーバー情報を構成し、Webサービス・ポートの作成時に引数としてClientProxyFeatureを渡すことができます。

例8-4 ポート作成時に引数としてClientProxyFeatureを渡す

package examples.webservices.simple_client;
import weblogic.wsee.jaxws.proxy
public class Main {
public static void main(String[] args) {
ComplexService test = new ComplexService();
ClientProxyFeature cpf = new ClientProxyFeature();
cpf.setProxyHost("localhost");
cpf.setProxyPort(8888);
cpf.setProxyUserName("proxyu");
cpf.setProxyPassword("proxyp");
ComplexPortType port = test.getComplexPortTypePort(cpf);
BasicStruct in = new BasicStruct();
in.setIntValue(999);
in.setStringValue("Hello Struct");
BasicStruct result = port.echoComplexType(in);
System.out.println("echoComplexType called. Result: " + result.getIntValue() + ", " + result.getStringValue());
}
}

または、次の例に示すように、ポートが作成された後にプロキシ・サーバー情報を構成することも可能です。この場合は、attachsPort()メソッドを実行し、既存のポートにClientProxyFeatureをアタッチします。

例8-5 ポート作成後のClientProxyFeatureの構成

package examples.webservices.simple_client;
import weblogic.wsee.jaxws.proxy
public class Main {
public static void main(String[] args) {
ComplexService test = new ComplexService();
ComplexPortType port = test.getComplexPortTypePort();
ClientProxyFeature cpf = new ClientProxyFeature();
cpf.setProxyHost("localhost");
cpf.setProxyPort(8888);
cpf.setProxyUserName("proxyu");
cpf.setProxyPassword("proxyp");
cpf.attachsPort(port);
BasicStruct in = new BasicStruct();
in.setIntValue(999);
in.setStringValue("Hello Struct");
BasicStruct result = port.echoComplexType(in);
System.out.println("echoComplexType called. Result: " + result.getIntValue() + ", " + result.getStringValue());
}
}

ClientProxyFeatureを構成し、クライアント・プロキシ設定を無効化するポートにアタッチしたら、プロキシ・ポートを負の値に設定します。例:

例8-6 クライアント・プロキシ設定の無効化

. . .
ClientProxyFeature cpf = new ClientProxyFeature();
cpf.setProxyPort(-1);\
cpf.attachsPort(port);
. . .

システム・プロパティを使用したプロキシ・サーバーの指定

プロキシ・サーバーの指定にシステム・プロパティを使用する場合は、クライアント・アプリケーションの記述は標準的な方式で行い、クライアント・アプリケーションの実行時に以下のシステム・プロパティを指定します。

次の表に、Javaシステム・プロパティをまとめます。

注意:
その場合は、proxySetのシステム・プロパティを設定することはできません。proxySetのシステム・プロパティが(proxySet=false)に設定されている場合、プロキシ・プロパティは無視され、プロキシは使用できません。

表8-4 プロキシ・サーバーの指定に使用するJavaシステム・プロパティ

プロパティ

説明

http.proxyHost=proxyHostまたはhttps.proxyHost=proxyHost

プロキシ・サーバー が動作しているホスト・コンピュータ名。HTTP over SSLに対してhttps.proxyHostを使用します。

http.proxyPort=proxyPortまたはhttps.proxy.Port=proxyPort

プロキシ・サーバーがリスニングしているポート。HTTP over SSLに対してhttps.proxyPortを使用します。

http.nonProxyHosts=hostname | hostname | ...

プロキシをバイパスし、直接アクセスするホストのリスト。各ホスト名を「|」文字で区切ります。このプロパティはHTTPおよびHTTPSの両方に適用されます。

以下のAntビルド・スクリプトの抜粋では、clients.InvokeMyServiceというクライアント・アプリケーションを呼び出す場合のJavaシステム・プロパティの設定例を示します。

<target name="run-client">
<java fork="true"
classname="clients.InvokeMyService"
failonerror="true">
<classpath refid="client.class.path"/>
<arg line="${http-endpoint}"/>
<jvmarg line=
"-Dhttp.proxyHost=${proxy-host}
-Dhttp.proxyPort=${proxy-port}
-Dhttp.nonProxyHosts=${myhost}"
/>
</java>
</target>

Webサービスを再デプロイする際にクライアント側で考慮すべき事項

WebLogic Serverでは本番再デプロイメントをサポートしています。つまり、更新後の新しいバージョンのWebLogic Webサービスを同じWebサービスの古いバージョンと並行してデプロイできます。

WebLogic Serverでは、新しいクライアントのリクエストのみが新しいバージョンに転送されるように、クライアント接続が自動的に管理されます。再デプロイメント時にすでにWebサービスに接続していたクライアントは、作業が完了するまで古いバージョンのサービスを使用し続け、それらの作業が完了した時点で、WebLogic Serverが古いWebサービスを自動的にリタイアします。

Webサービスの新しいバージョンで次のWebサービス・アーティファクトが変更されていなければ、その新しいバージョンで古いクライアント・アプリケーションを引き続き使用できます。

- Webサービスを記述するWSDL

- Webサービスに添付されたWS-Policyファイル

上記のアーティファクトのいずれかが変更されている場合、clientgen Antタスクを再び実行して、クライアント・アプリケーションで使用されるJAX-WSスタブを再生成する必要があります。

たとえば、Webサービスの新しいバージョンで操作のシグネチャを変更すると、Webサービスの新しいバージョンを記述するWSDLファイルも変更されます。この場合、JAX-WSスタブを再生成する必要があります。ただし、単に操作の実装のみを変更し、操作のパブリック・コントラクトは変更しない場合、既存のクライアント・アプリケーションを引続き使用できます。

Webサービスおよびクライアントを同一の管理対象サーバーにデプロイする場合のクライアントに関する考慮事項

Webサービスおよびクライアントを同一の管理対象サーバーにデプロイし、次のいずれかが該当する場合:

- Webサービス・クライアントは@WebServiceRefアノテーションを使用しますが、wsdlLocation要素の値は指定しません。

- Webサービス・クライアントが@WebServiceRefアノテーションのwsdlLocation要素を使用して、Webサービス・アプリケーションでパッケージ化されるWSDL(たとえば、@WebServiceRef(wsdlLocation="myService.wsdl"))とは反対に、ライブのWSDLの場所(たとえば、@WebServiceRef(wsdlLocation="http://xyz.com/myService?WSDL"))を参照します。

続いて、Webサービスとクライアントがデプロイされている管理対象サーバーを再起動するとき、アプリケーションは最初管理モードでデプロイされ、その後本番モードに遷移してHTTPリクエストを受け入れるため、デプロイメントの順序に関係なくWebサービス・クライアントは再デプロイに失敗する場合があります。この場合、サーバーが再起動したらアプリケーションを手動で再起動する必要があります。

Webサービスおよびクライアントを同一の管理対象サーバーにデプロイする場合、この状況を回避するために、Webサービス・アプリケーションの一部としてWSDLをパッケージ化し、@WebServiceRefアノテーションからパッケージ化されたバージョンを参照することをお薦めします。

9 JAX-WS Webサービス・クライアントの開発例

この章では、Java API for XML-based Web services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービス・クライアントの一般的な開発例を示します。

この章の内容は次のとおりです:

- JAX-WS Java SEクライアントの開発

- WebLogic WebサービスからのWebサービスの呼出し

各例では、簡単なWebLogic Webサービスを作成する手順や、デプロイ済のWebサービスから操作を呼び出す手順を示します。これらの例には基本的なJavaコードとAnt build.xmlファイルが含まれており、それらをユーザーの開発環境で使用してサンプルを再現することや、現在の開発環境とは別の環境で指示に従ってサンプルを作成して実行することができます。

例ではサンプルで使用されるプロセスやツールについては詳しく説明していません。詳細は、以降の章を参照してください。

注意:
高度なWebサービス機能を示すベスト・プラクティスの例については、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」および第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

JAX-WS Java SEクライアントの開発

注意:
WebLogic Serverで実行されている(WebLogic Serverクラスパスにアクセスする)任意のJava SEまたはJava EEアプリケーションからWebサービスを呼び出すことができます。WebLogic Serverライブラリが使用できない環境で実行されているスタンドアロンJavaアプリケーションからのWebサービスの呼出しは、JAX-WS Webサービスのこのリリースではサポートされていません。

クライアント・アプリケーションからデプロイ済のWebサービスの操作を呼び出す場合、WebサービスはWebLogic Serverにデプロイされている場合と、.NETなどの他のアプリケーション・サーバーにデプロイされている場合があります。知る必要があるのは、パブリック・コントラクト・ファイル、つまりWSDLのURLのみです。

Javaクライアント・アプリケーションを記述する他に、clientgen WebLogic WebサービスAntタスクを実行して、クライアント・アプリケーションがWebサービス操作を呼び出すために必要なアーティファクトも生成する必要があります。次のようなアーティファクトがあります。

- 呼出しの対象となる特定のWebサービスに対するServiceインタフェース実装のJavaクラス。

- JAXBデータ・バインディング・アーティファクト。

- WSDLファイルで指定されたユーザー定義XMLスキーマ・データ型のJavaクラス。

次の例では、「ユーザー定義のデータ型を使用するWebサービスの作成」で説明している、ComplexService WebLogic WebサービスのechoComplexType操作を呼び出すJavaクライアント・アプリケーションを作成する方法を示します。echoComplexType操作は、ユーザー定義のデータ型であるBasicStructをパラメータおよび戻り型として使用します。

注意:
この手順では、ComplexService Webサービスを作成してデプロイ済であると仮定しています。

1. WebLogic Server環境を設定します。
コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)スクリプトを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2. プロジェクト・ディレクトリを作成します。

prompt> mkdir /myExamples/simple_client

3. プロジェクト・ディレクトリの下に、srcディレクトリと、Javaクライアント・アプリケーション(この手順で後述)のパッケージ名に対応するサブディレクトリを作成します。

prompt> cd /myExamples/simple_client
prompt> mkdir src/examples/webservices/simple_client

4. プロジェクト・ディレクトリ内に標準のAnt build.xmlファイルを作成し、taskdef Antタスクを追加して、clientgenタスクの完全修飾Javaクラス名を指定します。

<project name="webservices-simple_client" default="all">
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
</project>

完全なサンプルbuild.xmlファイルについては、「Javaクライアント・アプリケーションをビルドするためのサンプルAntビルド・ファイル」を参照してください。完全なbuild.xmlファイルでは、クライアント・クラスの出力ディレクトリの名前を常にハード・コードして使用するのではなく、${clientclass-dir}などのプロパティを使用します。

5. 次のようなclientgenおよびjavac Antタスクの呼出しを、build-clientターゲット内にラップして、build.xmlファイルに追加します。

<target name="build-client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
destDir="output/clientclass"
packageName="examples.webservices.simple_client"
type="JAXWS"/>
<javac
srcdir="output/clientclass" destdir="output/clientclass"
includes="**/*.java"/>
<javac
srcdir="src" destdir="output/clientclass"
includes="examples/webservices/simple_client/*.java"/>
</target>

clientgen Antタスクでは、デプロイされたComplexService WebサービスのWSDLを使用して必要なアーティファクトを生成し、指定されたパッケージ名を使用してそれらをoutput/clientclassディレクトリに格納します。変数は、WebサービスをホストしているWebLogic Serverインスタンスの実際のホスト名とポートに置き換えてください。

この例では、パッケージ名はクライアント・アプリケーションと同じパッケージ名examples.webservices.simple_clientに設定されます。パッケージ名をクライアント・アプリケーションとは異なる名前に設定した場合は、適切なクラス・ファイルをインポートする必要があります。たとえば、examples.webservices.complexというパッケージ名にした場合、クライアント・アプリケーションの以下のクラス・ファイルをインポートする必要があります。

import examples.webservices.complex.BasicStruct;
import examples.webservices.complex.ComplexPortType;
import examples.webservices.complex.ComplexService;

clientgen Antタスクはexamples.webservices.simple_client.BasicStruct JavaBeanクラスも自動的に生成します。このクラスは、WSDLで指定されたユーザー定義のデータ型のJava表現です。

build-clientターゲットでは、clientgenの他に標準のjavac Antタスクも指定して、次の手順で説明するJavaプログラムを含む、すべてのJavaコードをクラス・ファイルにコンパイルします。

clientgen AntタスクのdestFile属性を使用すると、生成されたJavaファイルを自動的にコンパイルして、すべてのアーティファクトをJARファイルにパッケージ化できます。詳細と例については、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のclientgenに関する項を参照してください。

6. echoComplexType操作を呼び出すJavaクライアント・アプリケーション・ファイルを作成します。
任意のJava IDEまたはテキスト・エディタを開いて、「サンプルJavaクライアント・アプリケーション」で指定されたコードを使用してMain.javaというJavaファイルを作成します。

アプリケーションは標準JAX-WSのガイドラインに従って、clientgenによって生成されたServiceインタフェースのWebサービス固有の実装を使用してWebサービスの操作を呼び出します。詳細は、第8章「Webサービス・クライアントの開発」を参照してください。

7. Main.javaファイルをメイン・プロジェクト・ディレクトリのsrc/examples/webservices/simple_clientサブディレクトリに保存します。

8. コマンド・ラインでbuild-clientターゲットを指定して、clientgenおよびjavac Antタスクを実行します。

prompt> ant build-client

output/clientclassディレクトリを見て、clientgen Antタスクによって生成されたファイルとアーティファクトを確認します。

9. Mainアプリケーションの実行に使用される以下のターゲットをbuild.xmlファイルに追加します。

<path id="client.class.path">
<pathelement path="output/clientclass"/>
<pathelement path="${java.class.path}"/>
</path>
<target name="run" >
<java fork="true"
classname="examples.webservices.simple_client.Main"
failonerror="true" >
<classpath refid="client.class.path"/>
</target>

runターゲットはMainアプリケーションを呼び出し、デプロイされたWebサービスのWSDL URLを1つの引数として渡します。classpath要素では、<path>タスクで作成される参照を使用して、CLASSPATHにclientclassディレクトリが追加されます。

10. runターゲットを実行してechoComplexType操作を呼び出します。

prompt> ant run

呼出しに成功すると、次のような最終出力が表示されます。

run:
[java] echoComplexType called. Result: 999, Hello Struct

build.xmlファイルのbuild-clientおよびrunターゲットを使用して、開発プロセスの一環としてJavaクライアント・アプリケーションを繰返し更新、再ビルド、および実行できます。

サンプルJavaクライアント・アプリケーション

以下に、echoComplexType操作を呼び出す簡単なJavaクライアント・アプリケーションを示します。<clientgen> packageName属性はクライアント・アプリケーションと同じパッケージ名に設定されているため、<clientgen>生成ファイルをインポートする必要はありません。

package examples.webservices.simple_client;
/**
* This is a simple Java application that invokes the
* echoComplexType operation of the ComplexService web service.
*/
public class Main {
public static void main(String[] args) {
ComplexService test = new ComplexService();
ComplexPortType port = test.getComplexPortTypePort();
BasicStruct in = new BasicStruct();
in.setIntValue(999);
in.setStringValue("Hello Struct");
BasicStruct result = port.echoComplexType(in);
System.out.println("echoComplexType called. Result: " + result.getIntValue() + ", " + result.getStringValue());
}
}

Javaクライアント・アプリケーションをビルドするためのサンプルAntビルド・ファイル

次のbuild.xmlファイルでは、Javaクライアント・アプリケーションをビルドするタスクが定義されています。この例では、プロパティを使用してファイルを簡素化しています。

<project name="webservices-simple_client" default="all">
<!-- set global properties for this build -->
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="example-output" value="output" />
<property name="clientclass-dir" value="${example-output}/clientclass" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<target name="clean" >
<delete dir="${clientclass-dir}"/>
</target>
<target name="all" depends="clean,build-client,run" />
<target name="build-client">
<clientgen
type="JAXWS"
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.simple_client"/>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/simple_client/*.java"/>
</target>
<target name="run" >
<java fork="true"
classname="examples.webservices.simple_client.Main"
failonerror="true" >
<classpath refid="client.class.path"/>
</java>
</target>
</project>

WebLogic WebサービスからのWebサービスの呼出し

デプロイされたWebLogic Webサービス内からWebサービス(WebLogic、Microsoft .NETなど)を呼び出すことができます。

その手順は、「JAX-WS Java SEクライアントの開発」で説明した手順と似ていますが、この場合はclientgen Antタスクを実行してクライアント・スタブを生成するのではなく、jwsc Antタスク内で<jws>の子要素<clientgen>を使用します。jwsc Antタスクでは、生成されたクライアント・スタブが自動的に呼出し側のWebサービスのWARファイルにパッケージ化されるため、即座にWebサービスからアクセスできるようになります。その後で、標準JAX-WSのプログラミング・ガイドラインに従って、他のWebサービスを呼び出すWebサービスを実装するJWSファイルを作成します。

次の例では、「ユーザー定義のデータ型を使用するWebサービスの作成」で説明したComplexService WebサービスのechoComplexType操作を呼び出すJWSファイルを記述する方法を示します。

注意:
ComplexService Webサービスは正常にデプロイ済であると想定しています。

1. WebLogic Server環境を設定します。
コマンド・ウィンドウを開いて、ドメイン・ディレクトリのbinサブディレクトリにあるsetDomainEnv.cmd (Windows)またはsetDomainEnv.sh (UNIX)スクリプトを実行します。WebLogic Serverドメインのデフォルトの場所は、ORACLE_HOME/user_projects/domains/domainNameです。ここで、ORACLE_HOMEは、Oracle WebLogic Serverのインストール時にOracleホームとして指定したディレクトリ、domainNameは、ドメインの名前です。

2. プロジェクト・ディレクトリを作成します。

prompt> mkdir /myExamples/service_to_service

3. プロジェクト・ディレクトリの下に、srcディレクトリと、JWSおよびクライアント・アプリケーション・ファイル(この手順で後述)のパッケージ名に相当するサブディレクトリを作成します。

prompt> cd /myExamples/service_to_service
prompt> mkdir src/examples/webservices/service_to_service

4. ComplexService Webサービスを呼び出すWebサービスを実装するJWSファイルを作成します。
任意のJava IDEまたはテキスト・エディタを開いて、「サンプルClientServiceImpl.java JWSファイル」で指定されたJavaコードを使用してClientServiceImpl.javaというJavaファイルを作成します。

サンプルJWSファイルでは、1つのパブリック・メソッドcallComplexService()を含むClientServiceImplというJavaクラスが示されています。このJavaクラスでは、後でjwsc Antタスクで生成されるJAX-WSスタブと、BasicStruct JavaBean(同じくclientgenで生成される)をインポートしますが、BasicStruct JavaBeanは、ComplexService WebサービスのechoComplexType操作のパラメータと戻り値のデータ型です。

ClientServiceImpl Javaクラスでは1つのメソッドcallComplexService()を定義しています。このメソッドは、1つのパラメータBasicStructを取り、このパラメータがComplexService WebサービスのechoComplexType操作に渡されます。このメソッドは標準のJAX-WS APIを使用し、jwscによって生成されたスタブを使用して、ComplexServiceのServiceとPortTypeを取得します。その後で、echoComplexType操作を呼び出します。

5. ClientServiceImpl.javaファイルをsrc/examples/webservices/service_to_serviceディレクトリに保存します。

6. プロジェクト・ディレクトリ内に標準のAnt build.xmlファイルを作成して、次のタスクを追加します。

<project name="webservices-service_to_service" default="all">
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
</project>

taskdefタスクでは、jwsc Antタスクの完全なクラス名を定義しています。

この手順で説明される追加のターゲット(clean、deploy、undeploy、client、runなど)が含まれている、完全なサンプルbuild.xmlファイルについては、「ClientServiceをビルドするためのサンプルAntビルド・ファイル」を参照してください。完全なbuild.xmlファイルでは、EARディレクトリの名前を常にハード・コード化して使用するのではなく、${ear-dir}などのプロパティも使用しています。

7. 次のようなjwsc Antタスクの呼出しを、build-serviceターゲット内にラップして、build.xmlファイルに追加します。

<target name="build-service">
<jwsc
srcdir="src"
destdir="output/ClientServiceEar" >
<jws
file="examples/webservices/service_to_service/ClientServiceImpl.java"
type="JAXWS">
<WLHttpTransport
contextPath="ClientService" serviceUri="ClientService"
portName="ClientServicePort"/>
<clientgen
type="JAXWS"
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
packageName="examples.webservices.complex" />
</jws>
</jwsc>
</target>

この例では、jwsc Antタスクの<jws>要素の<clientgen>子要素で、jwscがJWSファイルをコンパイルするだけでなく、WSDLファイルに記述されているWebサービスを呼び出すために必要なクライアント・アーティファクトも生成およびコンパイルすることを指定しています。

この例では、パッケージ名はexamples.webservices.complexに設定され、これはクライアント・アプリケーションのパッケージ名examples.webservices.simple_clientとは異なります。そのため、クライアント・アプリケーションの適切なクラス・ファイルをインポートする必要があります。

import examples.webservices.complex.BasicStruct;
import examples.webservices.complex.ComplexPortType;
import examples.webservices.complex.ComplexService;

パッケージ名がクライアント・アプリケーションと同じパッケージ名に設定されている場合、インポートの呼出しは省略できます。

8. コマンド・ラインでbuild-serviceターゲットを指定して、jwsc Antタスクを実行します。

prompt> ant build-service

9. WebサービスをデプロイするWebLogic Serverインスタンスを起動します。

10. WebLogic Server管理コンソールまたはwldeploy Antタスクを使用して、エンタープライズ・アプリケーションにパッケージ化されたWebサービスをWebLogic Serverにデプロイします。いずれの場合でも、outputディレクトリにあるClientServiceEarエンタープライズ・アプリケーションをデプロイします。
wldeploy Antタスクを使用するには、以下のターゲットをbuild.xmlファイルに追加します。

<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="deploy">
<wldeploy action="deploy" name="ClientServiceEar"
source="ClientServiceEar" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>

wls.username、wls.password、wls.hostname、wls.port、およびwls.server.nameの値は、ご使用のWebLogic Serverインスタンスの対応する値で置き換えます。

deployターゲットを実行して、WARファイルをデプロイします。

prompt> ant deploy

11. ブラウザでWSDLを呼び出して、Webサービスが正しくデプロイされていることをテストします。

http://host:port/ClientService/ClientService?WSDL

Webサービスを呼び出すJavaクライアント・アプリケーションの作成例については、「JAX-WS Java SEクライアントの開発」を参照してください。

サンプルClientServiceImpl.java JWSファイル

echoComplexType操作を呼び出す簡単なWebサービス・クライアント・アプリケーションを次に示します。

package examples.webservices.service_to_service;

import javax.jws.WebService;
import javax.jws.WebMethod;
import javax.xml.ws.WebServiceRef;

// Import the BasicStruct data type, generated by clientgen and used
// by the ComplexService Web Service
import examples.webservices.complex.BasicStruct;

// Import the JAX-WS stubs generated by clientgen for invoking
// the ComplexService web service.
import examples.webservices.complex.ComplexPortType;
import examples.webservices.complex.ComplexService;

@WebService(name="ClientPortType", serviceName="ClientService",
targetNamespace="http://examples.org")
public class ClientServiceImpl {
// Use the @WebServiceRef annotation to define a reference to the
// ComplexService web service.
@WebServiceRef()
ComplexService test;

@WebMethod()
public String callComplexService(BasicStruct input, String serviceUrl)
{
// Create a port stub to invoke ComplexService
ComplexPortType port = test.getComplexPortTypePort();

// Invoke the echoComplexType operation of ComplexService
BasicStruct result = port.echoComplexType(input);
System.out.println("Invoked ComplexPortType.echoComplexType." );
return "Invoke went okay!  Here's the result: '" + result.getIntValue() +
",  " + result.getStringValue() + "'";
}
}

ClientServiceをビルドするためのサンプルAntビルド・ファイル

次のbuild.xmlファイルでは、クライアント・アプリケーションをビルドするタスクが定義されています。この例では、プロパティを使用してファイルを簡素化しています。

以下のbuild.xmlファイルでは、プロパティを使用してファイルを簡素化しています。

<project name="webservices-service_to_service" default="all">
<!-- set global properties for this build -->
<property name="wls.username" value="weblogic" />
<property name="wls.password" value="weblogic" />
<property name="wls.hostname" value="localhost" />
<property name="wls.port" value="7001" />
<property name="wls.server.name" value="myserver" />
<property name="ear.deployed.name" value="ClientServiceEar" />
<property name="example-output" value="output" />
<property name="ear-dir" value="${example-output}/ClientServiceEar" />
<property name="clientclass-dir" value="${example-output}/clientclasses" />
<path id="client.class.path">
<pathelement path="${clientclass-dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />
<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />
<taskdef name="wldeploy"
classname="weblogic.ant.taskdefs.management.WLDeploy"/>
<target name="all" depends="clean,build-service,deploy,client" />
<target name="clean" depends="undeploy">
<delete dir="${example-output}"/>
</target>
<target name="build-service">
<jwsc
srcdir="src"
destdir="${ear-dir}" >
<jws
file="examples/webservices/service_to_service/ClientServiceImpl.java"
type="JAXWS">
<WLHttpTransport
contextPath="ClientService" serviceUri="ClientService"
portName="ClientServicePort"/>
<clientgen
type="JAXWS"
wsdl="http://${wls.hostname}:${wls.port}/complex/ComplexService?WSDL"
packageName="examples.webservices.complex" />
</jws>
</jwsc>
</target>
<target name="deploy">
<wldeploy action="deploy" name="${ear.deployed.name}"
source="${ear-dir}" user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="undeploy">
<wldeploy action="undeploy" name="${ear.deployed.name}"
failonerror="false"
user="${wls.username}"
password="${wls.password}" verbose="true"
adminurl="t3://${wls.hostname}:${wls.port}"
targets="${wls.server.name}" />
</target>
<target name="client">
<clientgen
wsdl="http://${wls.hostname}:${wls.port}/ClientService/ClientService?WSDL"
destDir="${clientclass-dir}"
packageName="examples.webservices.service_to_service.client"
type="JAXWS"/>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/service_to_service/client/**/*.java"/>
</target>
<target name="run">
<java classname="examples.webservices.service_to_service.client.Main"
fork="true"
failonerror="true" >
<classpath refid="client.class.path"/>
</java>
</target>
</project>

第IV部

JAX-WS Webサービスの高度な機能の開発

第IV部では、WebLogic Server 12.1.3のJava API for XML-based Web Services (JAX-WS)を使用してWebLogic Webサービスの高度な機能を開発する方法について説明します。

ここで説明する内容は次のとおりです。

- 第10章「Web Services Addressingの使用」

- 第11章「非同期Webサービス・クライアントを開発するためのロードマップ」

- 第12章「非同期クライアントの開発」

- 第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」

- 第14章「Webサービスの信頼性のあるメッセージングの使用」

- 第15章「Webサービス原子性トランザクションの使用」

- 第16章「Fast Infosetを使用したXML転送の最適化」

- 第17章「SOAP Over JMSトランスポートの使用」

- 第18章「SOAPメッセージ・ハンドラの作成と使用」

- 第19章「SOAPフォルトを使用した例外処理」

- 第20章「バイナリ・データ転送の最適化」

- 第21章「Webサービス永続性の管理」

- 第22章「Webサービスのメッセージ・バッファリングの構成」

- 第23章「クラスタ内のWebサービスの管理」

- 第24章「プロバイダベース・エンドポイントおよびディスパッチ・クライアントを使用したSOAPメッセージの操作」

- 第25章「SOAPヘッダーの送受信」

- 第26章「コールバックの使用」

- 第27章「動的プロキシ・クライアントの開発」

- 第28章「Webサービスのエンドポイントのパブリッシュ」

- 第29章「XMLカタログの使用」

- 第30章「XML Over HTTPを使用するWebサービスのプログラミング」

- 第31章「HTTPセッションを使用したステートフルJAX-WS Webサービスのプログラミング」

- 第32章「Webサービスのテストおよび監視」

10 Web Services Addressingの使用

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスで、Web Services Addressing (WS-Addressing)を使用する方法について説明します。

この章の内容は次のとおりです:

- WS-Addressingの概要

- WebサービスでのWS-Addressingの有効化

- Webサービス・クライアントでのWS-Addressingの有効化

- WS-AddressingのActionプロパティの関連付け

- 匿名WS-Addressingの構成

WS-Addressingの概要

WS-Addressingは、Webサービスおよびそれに関連するメッセージをアドレッシングするための、トランスポートに依存しないメカニズムを提供します。WS-Addressingを使用すると、エンドポイントはSOAPヘッダー内で一意かつ明確に定義されます。

WS-Addressingには、トランスポートに依存しないアドレッシングを可能にする次の2つの主要なコンポーネントがあります。

- エンドポイント参照(EPR): Webサービス・エンドポイントのアドレッシングに必要な情報を通知します。

- メッセージ・アドレッシング・プロパティ: エンドツーエンドのメッセージ特性(ソースおよび宛先のエンドポイントとメッセージIDへのアドレッシングなど)を通知します。これにより、メッセージに対して基礎となるトランスポートからは独立した共通のアドレッシングが可能になります。
メッセージ・アドレッシング・プロパティには、表10-1に定義されているプロパティを1つ以上含めることができます。wsa:Action以外のプロパティはすべてオプションです。

表10-1 WS-Addressingのメッセージ・アドレッシング・プロパティ

コンポーネント

説明

wsa:To

宛先。指定しない場合は、デフォルトの宛先(http://www.w3.org/2005/08/addressing/anonymous)が設定されます。

wsa:From

ソース・エンドポイント。

wsa:ReplyTo

リプライ・エンドポイント。指定しない場合は、デフォルトのリプライ・エンドポイント(http://www.w3.org/2005/08/addressing/anonymous)が設定されます。

wsa:FaultTo

フォルト・エンドポイント。

wsa:Action

必要なアクション。

WS-Addressingが有効な場合、このプロパティは必須です。これは暗黙的または明示的に構成できます(「WS-Addressing Actionプロパティの関連付け」を参照)。

wsa:MessageID

一意のメッセージID。

wsa:RelatesTo

メッセージに関連付けられたメッセージID。関連メッセージが複数ある場合には、この要素を繰り返すことができます。このプロパティの属性としてRelationshipTypeを指定できます。デフォルト値はhttp://www.w3.org/2005/08/addressing/replyです。

wsa:ReferenceParameters

通知する必要がある参照パラメータ。

例10-1は、WS-Addressingを有効にしてHTTP 1.2で送信されるSOAP 1.2リクエスト・メッセージを示します。太字で示されているように、WS-Addressingは、一意のメッセージID (wsa:MessageID)、宛先(wsa:To)エンドポイント、リプライ・エンドポイント(wsa:ReplyTo)、および必要なアクション(wsa:Action)を定義するための、トランスポートに依存しないメカニズムを提供します。

例10-1 WS-Addressingを使用したSOAP 1.2メッセージ: リクエスト・メッセージ

<S:Envelope xmlns:S="http://www.w3.org/2003/05/soap-envelope"
xmlns:wsa="http://www.w3.org/2005/08/addressing/">
<S:Header>
<wsa:MessageID>
http://example.com/someuniquestring
</wsa:MessageID>
<wsa:ReplyTo
<wsa:Address>http://example.com/Myclient</wsa:Address>
</wsa:ReplyTo>
<wsa:To>
http://example.com/fabrikam/Purchasing
</wsa:To>
<wsa:Action>
http://example.com/fabrikam/SubmitPO
</wsa:Action>
<S:Header>
<S:Body>
...
</S:Body>
</S:Envelope>

このメッセージへのレスポンスは、例10-2のようになります。RelatesToプロパティによってレスポンス・メッセージと元のリクエスト・メッセージが関連付けられます。

例10-2 WS-Addressingを使用しないSOAP 1.2メッセージ: レスポンス・メッセージ

<S:Envelope
xmlns:S="http://www.w3.org/2003/05/soap-envelope"
xmlns:wsa="http://www.w3.org/2005/08/addressing">
<S:Header>
<wsa:MessageID>http://example.com/someotheruniquestring</wsa:MessageID>
<wsa:RelatesTo>http://example.com/someuniquestring</wsa:RelatesTo>
<wsa:To>http://example.com/MyClient/wsa:To>
<wsa:Action>
http://example.com/fabrikam/SubmitPOAck
</wsa:Action>
</S:Header>
<S:Body>
...
</S:Body>
</S:Envelope>

WS-Addressingは、次のWebLogic JAX-WS拡張機能で使用されます。

- 非同期のクライアント・トランスポート(第12章「非同期クライアントの開発」を参照)。

- WS-ReliableMessaging(第14章「Webサービスの信頼性のあるメッセージングの使用」を参照)。

- コールバック(第26章「コールバックの使用」を参照)。

次の項では、WebサービスまたはクライアントでWS-Addressingを有効にし、アクション・プロパティおよびフォルト・プロパティを明示的に定義する方法について説明します。

サポートされているWS-Addressing標準に関する説明

WebLogic Webサービスは、次のWeb Service Addressingの標準をサポートしています。

- W3C WS-Addressing(http://www.w3.org/2002/ws/addr/を参照)

- Member Submission(http://www.w3.org/Submission/ws-addressing/を参照)

この章では、W3C WS-Addressingの使用についてのみを取り上げます。

WebサービスでのWS-Addressingの有効化

デフォルトでは、WS-AddressingはWebサービス・エンドポイントで無効化されています。そのため、受信したWS-Addressingヘッダーはすべて無視されます。WebサービスでのWS-AddressingをJavaまたはWSDLから有効にするには、次の各項に従います。

- WebサービスでのWS-Addressingの有効化(Javaから始める場合)

- WebサービスでのWS-Addressingの有効化(WSDLから始める場合)

Webサービス・エンドポイントでWS-Addressingを有効にすると次のようになります。

- すべてのWS-Addressingヘッダーがエンドポイントで認識されます。つまり、mustUnderstandを有効にしてWS-Addressingヘッダーを受信した場合、フォルトはスローされません。

- 受信したWS-Addressingヘッダーは、次のことを確認するために検証されます。

- 構文が正しいか

- 要素数が正しいか

- SOAPヘッダーのwsa:Actionヘッダーが操作で必要なものと一致しているか

- クライアントに返されるレスポンス・メッセージには必要なWS-Addressingヘッダーが格納されます。

WebサービスでのWS-Addressingの有効化(Javaから始める場合)

WebサービスでのWS-AddressingをJavaから有効にするには、Webサービス・クラスでjava.xml.ws.soap.Addressingアノテーションを使用します。必要に応じて、表10-2に定義されているBoolean属性を1つ以上渡すことができます。

表10-2 @Addressingアノテーションの属性

属性

説明

enabled

WS-Addressingを有効にするかどうかを指定します。有効な値は、true(有効)およびfalse(無効)です。この属性のデフォルト値はtrueです。

required

インバウンド・メッセージに対してWS-Addressingルールを適用するかどうかを指定します。有効な値は、true(適用する)およびfalse(適用しない)です。falseに設定すると、WS-Addressingが有効かどうかを確認するためのチェックがインバウンド・メッセージに対して行われ、有効な場合はルールが適用されます。この属性のデフォルト値はfalseです。

有効にすると、wsaw:UsingAddressing要素が、対応するwsdl:binding要素内に生成されます。詳細は、「WebサービスでのWS-Addressingの有効化(WSDLから始める場合)」を参照してください。

次の例では、WS-AddressingをJavaから有効にする方法を示します。この例では、エンドポイントでWS-Addressingが実行されます(requiredをtrueに設定)。

例10-3 WebサービスでのWS-Addressingの有効化(Javaから始める場合)

package examples;
import javax.jws.WebService;
import javax.xml.ws.soap.Addressing;

@WebService(name="HelloWorld", serviceName="HelloWorldService")
@Addressing(enabled=true, required=false)

public class HelloWorld {
public String sayHelloWorld(String message) throws MissingName { ... }
}

WebサービスでのWS-Addressingの有効化(WSDLから始める場合)

WebサービスでのWS-AddressingをWSDLから有効にするには、wsaw:UsingAddressing要素を対応するwsdl:binding要素に追加します。必要に応じて、wsdl:required Boolean属性を追加して、インバウンド・メッセージに対してWS-Addressingルールを適用するかどうかを指定できます。この属性のデフォルト値はfalseです。

次の例では、WS-AddressingをWSDLから有効にする方法を示します。この例では、エンドポイントでWS-Addressingが実行されます(wsdl:requiredをtrueに設定)。

例10-4 WebサービスでのWS-Addressingの有効化(WSDLから始める場合)

...
<binding name="HelloWorldPortBinding" type="tns:HelloWorld">
<wsaw:UsingAddressing wsdl:required="true" />
<soap:binding transport="http://schemas.xmlsoap.org/soap/http"
style="document"/>
<operation name="sayHelloWorld">
<soap:operation soapAction=""/>
<input>
<soap:body use="literal"/>
</input>
<output>
<soap:body use="literal"/>
</output>
<fault name="MissingName">
<soap:fault name="MissingName" use="literal"/>
</fault>
</operation>
</binding>
...

Webサービス・クライアントでのWS-Addressingの有効化

WS-Addressingは、Webサービス・クライアントで暗黙的または明示的に有効にできます。クライアントで有効にすると、次のようになります。

- クライアントが受信したすべてのWS-Addressingヘッダーが認識されます。つまり、mustUnderstandを有効にしてWS-Addressingヘッダーを受信した場合、フォルトはスローされません。

- JAX-WSランタイムは次のことを行います。

- すべてのwsaw:Action要素(wsdl:operationのinput、outputおよびfault要素など)を、生成されたサービス・エンドポイント・インタフェース(SEI)のjavax.xml.ws.Actionおよびjavax.xml.ws.FaultActionアノテーションにマップします。

- アウトバウンド・リクエストにAction、To、MessageIDおよび匿名のReplyToヘッダーを生成します。

次の項では、Webサービス・クライアントでWS-Addressingを明示的および暗黙的に有効にする方法、およびWS-Addressingを明示的に無効にする方法について説明します。

- Webサービス・クライアントでのWS-Addressingの明示的な有効化

- Webサービス・クライアントでのWS-Addressingの暗黙的な有効化

- Webサービス・クライアントでのWS-Addressingの無効化

Webサービス・クライアントでのWS-Addressingの明示的な有効化

Webサービス・クライアントでは、javax.xml.ws.ServiceオブジェクトのgetPortまたはcreateDispatchメソッドにjavax.xml.ws.soap.AddressingFeatureを引数として渡すことにより、WS-Addressingを明示的に有効にできます。必要に応じて、表10-3に定義されているBooleanパラメータを1つ以上渡すことができます。

表10-3 AddressingFeature機能のパラメータ

パラメータ

説明

enabled

アウトバウンド・メッセージに対してWS-Addressingを有効にするかどうかを指定します。有効な値は、true(有効)およびfalse(無効)です。この属性のデフォルト値はtrueです。

required

インバウンド・メッセージに対してWS-Addressingルールを適用するかどうかを指定します。有効な値は、true(適用する)およびfalse(適用しない)です。falseに設定すると、WS-Addressingが有効かどうかを確認するためのチェックがインバウンド・メッセージに対して行われ、有効な場合はルールが適用されます。この属性のデフォルト値はfalseです。

次の例では、Webサービス・プロキシの作成時に、AddressingFeatureをgetPortメソッドに渡して、Webサービス・クライアントのWS-Addressingを有効にする方法を示します。

例10-5 Webサービス・プロキシのWebサービス・クライアントでのWS-Addressingの有効化

package examples.client;

import javax.xml.namespace.QName;
import java.net.MalformedURLException;
import java.net.URL;
import examples.client.MissingName_Exception;
import javax.xml.ws.soap.AddressingFeature;

public class Main {
public static void main(String[] args) throws MissingName_Exception {
HelloWorldService service;

try {
service = new HelloWorldService(new URL(args[0] + "?WSDL"),
new QName("http://examples/", "HelloWorldService") );
} catch (MalformedURLException murl) { throw new RuntimeException(murl); }

HelloWorld port = service.getHelloWorldPort(
new AddressingFeature(true, true));
...
}
}

次の例では、Dispatchインスタンスの作成時に、AddressingFeatureをcreateDispatchメソッドに渡してWebサービス・クライアントのWS-Addressingを有効にする方法を示します。

例10-6 DispatchインスタンスのWebサービス・クライアントでのWS-Addressingの有効化

...
HelloWorld port = service.getHelloWorldPort(new AddressingFeature(true));
...

Webサービス・クライアントでのWS-Addressingの暗黙的な有効化

wsaw:UsingAddressing拡張要素がWSDLに存在する場合、WS-Addressingは暗黙的に有効になります。詳細は、「WebサービスでのWS-Addressingの有効化(WSDLから始める場合)」を参照してください。

Webサービス・クライアントでのWS-Addressingの無効化

Webサービス・クライアントでは、独自のWS-Addressing処理モジュールを使用する場合など、WS-Addressing処理の明示的な無効化が必要となる場合があります。たとえば、MESSAGEモードのディスパッチ・クライアントを使用して非匿名のReplyToおよびFaultTo処理を実行する場合などです。

次の例では、Webサービス・プロキシの作成時に、Webサービス・クライアントのWS-Addressingを明示的に無効にする方法を示します。この例では、enabledをfalseに設定してAddressingFeature機能を呼び出します。

例10-7 Webサービス・クライアントでのWS-Addressingの無効化

...
new AddNumbersImplService().getAddNumbersImplPort(new javax.xml.ws.AddressingFeature(false));
...

WS-AddressingのActionプロパティの関連付け

WS-Addressingは属性wsaw:Actionを定義します。この属性を使用して、WebサービスにWS-AddressingのActionメッセージ・アドレッシング・プロパティを明示的に関連付けることができます。デフォルトでは、WS-Addressingが有効で、Webサービスに明示的に関連付けられているアクションがない場合は、暗黙的なアクションの関連付けが行われます。

次の項では、WS-AddressingのActionプロパティを明示的または暗黙的に関連付ける方法を説明します。

- WS-AddressingのActionプロパティの明示的な関連付け(Javaから始める場合)

- WS-AddressingのActionプロパティの明示的な関連付け(WSDLから始める場合)

- WS-AddressingのActionプロパティの暗黙的な関連付け

WS-AddressingのActionプロパティの明示的な関連付け(Javaから始める場合)

WS-AddressingのActionプロパティをJavaから明示的にWebサービスに関連付けるには、javax.xml.ws.Actionおよびjavax.xml.ws.FaultActionアノテーションを使用します。

必要に応じて、表10-4に定義されている属性を@Actionアノテーションに対して1つ以上渡すことができます。

表10-4 @Actionアノテーションの属性

属性

説明

input

操作のinputメッセージに対応するActionメッセージ・アドレッシング・プロパティを関連付けます。

output

操作のoutputメッセージに対応するActionメッセージ・アドレッシング・プロパティを関連付けます。

fault

操作のfaultメッセージに対応するActionメッセージ・アドレッシング・プロパティを関連付けます。表10-5に記載されているように、SOAP障害にマップされ、SOAPフォルトにマップし、明示的な関連付けが必要となる例外については、@FaultActionアノテーションを使用して指定する必要があります。

表10-4に定義されている属性を@FaultActionアノテーションに対して1つ以上渡すことができます。

表10-5 @FaultActionアノテーションの属性

属性

説明

className

例外クラスの名前。この属性は必須です。

value

例外のWS-Addressing Actionメッセージ・アドレッシング・プロパティの値。

WS-AddressingのActionプロパティを明示的に関連付けると、wsaw:Action属性が、wsdl:portType要素内の対応するinput要素、output要素およびfault要素に生成されます。詳細は、「WebサービスでのWS-Addressingの有効化(WSDLから始める場合)」を参照してください。

次の例では、@Actionおよび@FaultActionアノテーションを使用して、input、output、およびfaultメッセージに対応するWS-AddressingのActionメッセージ・アドレッシング・プロパティをsayHelloWorldに明示的に関連付ける方法を示します。

例10-8 アクションの明示的な関連付けの例(Javaから始める場合)

...
@Action(
input = "http://examples/HelloWorld/sayHelloWorldRequest",
output = "http://examples/HelloWorld/sayHelloWorldResponse",
fault = { @FaultAction(className = MissingName.class,
value = "http://examples/MissingNameFault")})

public String sayHelloWorld(String message) throws MissingName {
...

定義すると、エンドポイントのwsdl:operation要素内の対応するinput要素、output要素およびfault要素にwsaw:Action要素が生成されます。これらの要素の詳細は、「WS-Addressing Actionプロパティの明示的な関連付け(WSDLから始める場合)」を参照してください。

WS-AddressingのActionプロパティの明示的な関連付け(WSDLから始める場合)

WS-AddressingのActionプロパティをWSDLから明示的にWebサービスに関連付けるには、wwsaw:Action要素を対応するwsdl:binding要素に追加します。必要に応じて、wsdl:required Boolean属性を追加して、インバウンド・メッセージに対してWS-Addressingルールを適用するかどうかを指定できます。この属性のデフォルト値はfalseです。

次の例では、WSDLファイルで、HelloWorldエンドポイントのsayHelloWorldメソッドのinput、outputおよびfaultメッセージにWS-AddressingのActionメッセージ・アドレッシング・プロパティを明示的に関連付ける方法を示します。

例10-9 アクションの明示的な関連付けの例(WSDLから始める場合)

...
<portType name="HelloWorld">
<operation name="sayHelloWorld">
<input wsaw:Action="http://examples/HelloWorld/sayHelloWorldRequest"
message="tns:sayHelloWorld"/>
<output wsaw:Action="http://examples/HelloWorld/sayHelloWorldResponse"
message="tns:sayHelloWorldResponse"/>
<fault message="tns:MissingName" name="MissingName"
wsaw:Action="http://examples/MissingNameFault"/>
</operation>
</portType>
...

WS-AddressingのActionプロパティの暗黙的な関連付け

WS-Addressingが有効で、WSDLに明示的なアクションが定義されていない場合は、クライアントは次の形式を使用して暗黙的なwsa:Actionヘッダーを送信します。

- inputメッセージ・アクション: targetNamespace/portTypeName/inputName

- outputメッセージ・アクション: targetNamespace/portTypeName/outputName

- faultメッセージ・アクション: targetNamespace/portTypeName/operationName/Fault/FaultName

targetNamespace/portTypeName/[inputName | outputName]

たとえば、次のWSDLからの抜粋のようになります。

<definitions targetNamespace="http://examples/"...>
...
<portType name="HelloWorld">
<operation name="sayHelloWorld">
<input message="tns:sayHelloWorld" name="sayHelloRequest"/>
<output message="tns:sayHelloWorldResponse" name="sayHelloResponse"/>
<fault message="tns:MissingName" name="MissingName" />
</operation>
</portType>
...
</definitions>

デフォルトのinputおよびoutputアクションは次のように定義されます。

- inputメッセージ・アクション: http://examples/HelloWorld/sayHelloRequest

- outputメッセージ・アクション: http://examples/HelloWorld/sayHelloResponse

- faultメッセージ・アクション: http://examples/HelloWorld/sayHelloWorld/Fault/MissingName

WSDLでinputまたはoutputメッセージ名が指定されていない場合は、それぞれ操作名にRequestまたはResponseが追加された名前が使用されます。たとえば、sayHelloWorldRequestまたはsayHelloWorldResponseのようになります。

匿名WS-Addressingの構成

場合によって、ファイアウォールやDHCP (Dynamic Host Configuration Protocol)などのネットワーク・テクノロジが使用されている環境では、特定のエンドポイントに対してグローバルにアクセス可能なURIの使用が禁止されていることがあります。アドレッシングできないエンドポイントとのメッセージ交換を可能にするために、WS-Addressingの仕様ではwsaw:Anonymous要素を使用した「匿名」エンドポイントがサポートされています。

wsaw:Anonymous要素には表10-6に定義されているいずれかの値を設定できます。

表10-6 wsaw:Anonymous要素の有効な値

値

説明

optional

リクエスト・メッセージのレスポンス・エンドポイントEPRに匿名URIを含めることができます。

required

リクエスト・メッセージのレスポンス・エンドポイントEPRに匿名URLを含める必要があります。そうしないと、InvalidAddressingHeaderフォルトが返されます。

prohibited

リクエスト・メッセージのレスポンス・エンドポイントEPRに匿名URIを含めないでください。そうしないと、InvalidAddressingHeaderフォルトが返されます。

匿名WS-Addressingを構成するには:

1. WebサービスでWS-Addressingを有効にし、wsaw:UsingAddressing要素を対応するwsdl:binding要素に追加します。詳細は、「WebサービスでのWS-Addressingの有効化(WSDLから始める場合)」を参照してください。

注意:
匿名WS-Addressingが有効な場合は、wsaw:UsingAddressing要素でwsdl:required属性を有効にしないでください。

2. wsaw:Anonymous要素をwsdl:binding要素内のwsdl:operationに追加します。

次の例では、WSDLファイルで匿名WS-Addressingを有効にする方法を示します。この例では、匿名アドレッシングは必須です。

例10-10 Webサービスでの匿名WS-Addressingの有効化

...
<binding name="HelloWorldPortBinding" type="tns:HelloWorld">
<wsaw:UsingAddressing wsdl:required="true" />
<soap:binding transport="http://schemas.xmlsoap.org/soap/http"
style="document"/>
<operation name="sayHelloWorld">
<soap:operation soapAction=""/>
<input>
<soap:body use="literal"/>
</input>
<output>
<soap:body use="literal"/>
</output>
<fault name="MissingName">
<soap:fault name="MissingName" use="literal"/>
</fault>
</operation>
<wsaw:Anonymous>required</wsaw:Anonymous>
</binding>
...

11 非同期Webサービス・クライアントを開発するためのロードマップ

この章では、WebLogic Server 12.1.3用のJava API for XML Web Services (JAX-WS)用の非同期WebLogic Webサービス・クライアントを開発するためのベスト・プラクティスについて説明します。

表11-1では、非同期Webサービス・クライアントを開発するためのベスト・プラクティスとその例を示します。これらのガイドラインは、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」で示されている一般的なガイドラインと併せて使用する必要があります。

信頼性のあるWebサービス・クライアントの開発の際のベスト・プラクティスについては、第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

注意:
次の表でクライアント・インスタンスは、ポートまたはディスパッチ・インスタンスです。

表11-1 非同期Webサービス・クライアントを開発するためのロードマップ

ベスト・プラクティス

説明

非同期およびディスパッチ・コールバック処理のためにポートベースの非同期コールバック・ハンドラAsyncClientHandlerFeatureを定義します。

拡張性があり、JVMを再起動しても維持されるため、非同期呼び出しを使用するときのベスト・プラクティスとして、AsyncClientHandlerFeatureを使用することをお薦めします。このハンドラは(持続可能かどうかに関係なく)任意のクライアントで使用できます。詳細は、「非同期ハンドラ・インタフェースの開発」を参照してください。

シングルトン・ポート・インスタンスを定義し、(デプロイメント時に)クライアント・コンテナを初期化するときに初期化します。

シングルトン・ポートの作成:

- デプロイメント時に公開する非同期レスポンス・エンドポイントをトリガーします。

- VMの再起動後にシングルトン・ポート・インスタンスを再初期化することで、障害リカバリをサポートします。

クラスタ内では、シングルトン・ポートを初期化すると、クラスタ内のすべてのメンバー・サーバーが非同期レスポンス・エンドポイントをパブリッシュすることが保証されます。これによって、非同期レスポンス・メッセージが任意のメンバー・サーバーに配信され、必要に応じてインプレース・クラスタ・ルーティングを介して正しいサーバーに転送されることが保証されます。詳細は、「非同期Webサービス・メッセージングのクラスタリングの考慮事項」を参照してください。

ファイアウォールの内側にあるクライアントに接続作成を使用する場合は、接続作成ポーリング間隔をシナリオに対して現実的な値に設定します。

接続作成のポーリング間隔は、不必要なポーリング・オーバーヘッドを避けることができる大きな値で、なおかつ遅れずにレスポンスを取得できる十分に小さい値に設定する必要があります。接続作成ポーリング間隔の推奨される値は、呼び出されるWebサービスの予想される平均レスポンス時間の半分です。接続作成ポーリング間隔の設定の詳細は、「ポーリング間隔の構成」を参照してください。

注意: このベスト・プラクティスは、例11-1では示されていません。

JAX-WS参照実装(RI)を使用している場合は、AsyncHandler<T>インタフェースを実装します。

AsyncHandler<T>インタフェースを使用する方が、Response<T>インタフェースを使用するより効率的です。詳細および例は、「JAX-WS参照実装の使用」を参照してください。

注意: このベスト・プラクティスは、例11-1では示されていません。

ワーク・マネージャを定義し、スレッド・プールの最小サイズ制限(min-threads-constraint)を、最低でもサービスに対して予想される同時リクエスト数または同時レスポンス数と同じ値に設定します。

たとえば、Webサービス・クライアントが20個のリクエストを立て続けに発行する場合、そのクライアントをホストするアプリケーションで推奨されるスレッド・プールの最小サイズ制約の値は20です。構成した制約値が小さすぎると、受信処理で処理スレッドの空き待ちが発生するためパフォーマンスが大幅に低下するおそれがあります。

スレッド・プールの最小サイズ制約の詳細は、『Oracle WebLogic Serverサーバー環境の管理』の制約に関する項を参照してください。

次の例では、非同期Webサービス・クライアントを開発するためのベスト・プラクティスを示します。

例11-1 非同期Webサービス・クライアントのベスト・プラクティスの例

import java.io.*;
import java.util.*;

import javax.servlet.*
import javax.xml.ws.*

import weblogic.jws.jaxws.client.ClientIdentityFeature;
import weblogic.jws.jaxws.client.async.AsyncClientHandlerFeature;
import weblogic.jws.jaxws.client.async.AsyncClientTransportFeature;

import com.sun.xml.ws.developer.JAXWSProperties;

/**
* Example client for invoking a web service asynchronously.
*/
public class BestPracticeAsyncClient
extends GenericServlet {

private static final String MY_PROPERTY = "MyProperty";

private BackendServiceService _service;
private WebServiceFeature[] _features;
private BackendService _singletonPort;

private static String _lastResponse;
private static int _requestCount;

@Override
public void init()
throws ServletException {

// Only create the web service object once as it is expensive to create repeatedly.
if (_service == null) {
_service = new BackendServiceService();
}

// Best Practice: Use a stored list of features, including client ID, to create client
// instances.
// Define all features for the web service client instance, including client ID, so that they
// are consistent each time the client instance is created. For example:
// _service.getBackendServicePort(_features);

List<WebServiceFeature> features = new ArrayList<WebServiceFeature>();

// Best Practice: Explicitly define the client ID.
ClientIdentityFeature clientIdFeature =
new ClientIdentityFeature("MyBackendServiceAsyncClient");
features.add(clientIdFeature);

// Asynchronous endpoint
AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(getServletContext());
features.add(asyncFeature);

// Best Practice: Define a port-based asynchronous callback handler,
// AsyncClientHandlerFeature, for asynchronous and dispatch callback handling.
BackendServiceAsyncHandler handler =
new BackendServiceAsyncHandler() {
// This class is stateless and should not depend on
// having member variables to work with across restarts.
public void onDoSomethingResponse(Response<DoSomethingResponse> res) {
// ... Handle Response ...
try {
DoSomethingResponse response = res.get();
res.getContext();
_lastResponse = response.getReturn();
System.out.println("Got async response: " + _lastResponse);
// Retrieve the request property. This property can be used to
// 'remember' the context of the request and subsequently process
// the response.
Map<String, Serializable> requestProps =
(Map<String, Serializable>)
res.getContext().get(JAXWSProperties.PERSISTENT_CONTEXT);
String myProperty = (String)requestProps.get(MY_PROPERTY);
System.out.println("Got MyProperty value propagated from request: "+
myProperty);
} catch (Exception e) {
_lastResponse = e.toString();
e.printStackTrace();
}
}
};
AsyncClientHandlerFeature handlerFeature =
new AsyncClientHandlerFeature(handler);
features.add(handlerFeature);

// Set the features used when creating clients with
// the client ID "MyBackendServiceAsyncClient".

_features = features.toArray(new WebServiceFeature[features.size()]);

// Best Practice: Define a singleton port instance and initialize it when
// the client container initializes (upon deployment).
// The singleton port will be available for the life of the servlet.
// Creation of the singleton port triggers the asynchronous response endpoint to be published
// and it will remain published until our container (Web application) is undeployed.
// Note, the destroy() method will be called before this.
// The singleton port ensures proper/robust operation in both
// recovery and clustered scenarios.
_singletonPort = _service.getBackendServicePort(_features);
}

@Override
public void service(ServletRequest req, ServletResponse res)
throws ServletException, IOException {

// TODO: ... Read the servlet request ...

// For this simple example, echo the _lastResponse captured from
// an asynchronous DoSomethingResponse response message.

if (_lastResponse != null) {
res.getWriter().write(_lastResponse);
_lastResponse = null; // Clear the response so we can get another
return;
}

// Set _lastResponse to NULL to to support the invocation against
// BackendService to generate a new response.

// Best Practice: Synchronize use of client instances.
// Create another client instance using the *exact* same features used when creating _
// singletonPort. Note, this port uses the same client ID as the singleton port
// and it is effectively the same as the singleton
// from the perspective of the web services runtime.
// This port will use the asynchronous response endpoint for the client ID,
// as it is defined in the _features list.
BackendService anotherPort =
_service.getBackendServicePort(_features);

// Set the endpoint address for BackendService.
((BindingProvider)anotherPort).getRequestContext().
put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://localhost:7001/BestPracticeService/BackendService");

// Add a persistent context property that will be retrieved on the
// response. This property can be used as a reminder of the context of this
// request and subsequently process the response. This property will *not*
// be passed over the wire, so the properties can change independent of the
// application message.
Map<String, Serializable> persistentContext =
(Map<String, Serializable>)((BindingProvider)anotherPort).
getRequestContext().get(JAXWSProperties.PERSISTENT_CONTEXT);
String myProperty = "Request " + (++_requestCount);
persistentContext.put(MY_PROPERTY, myProperty);
System.out.println("Request being made with MyProperty value: " +
myProperty);

// Make the asychronous invocation. The asynchronous handler implementation (set
// into the AsyncClientHandlerFeature above) receives the response.
String request = "Dance and sing";
System.out.println("Invoking DoSomething asynchronously with request: " +
request);
anotherPort.doSomethingAsync(request);

// Return a canned string indicating the response was not received
// synchronously. Client will need to invoke the servlet again to get
// the response.
res.getWriter().write("Waiting for response...");

// Best Practice: Explicitly close client instances when processing is complete.
// If not closed explicitly, the port will be closed automatically when it goes out of scope.
((java.io.Closeable)anotherPort).close();
}

@Override
public void destroy() {

try {
// Best Practice: Explicitly close client instances when processing is complete.
// Close the singleton port created during initialization. Note, the asynchronous
// response endpoint generated by creating _singletonPort *remains*
// published until our container (Web application) is undeployed.
((java.io.Closeable)_singletonPort).close();

// Upon return, the Web application is undeployed, and the asynchronous
// response endpoint is stopped (unpublished). At this point,
// the client ID used for _singletonPort will be unregistered and will no longer be
// visible from the Administration Console and WLST.
} catch (Exception e) {
e.printStackTrace();
}
}
}

12 非同期クライアントの開発

この章では、Java API for XML Web Services (JAX-WS)を使用したfor WebLogic Server 12.1.3の非同期WebLogic Webサービス・クライアントの開発方法について説明します。

この章の内容は次のとおりです:

- Webサービスの非同期呼出しの概要

- Webサービスを非同期に呼び出す手順

- Webサービスを非同期に呼び出すためのサーバーの構成

- Webサービスを非同期に呼び出すためのクライアント・アーティファクトの構築

- スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)

- ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)

- JAX-WS参照実装の使用

- レスポンスへのリクエスト・コンテキストの伝播

- 非同期Webサービス呼出しのモニタリング

- 非同期Webサービス・メッセージングのクラスタリングの考慮事項

注意:
第11章「非同期Webサービス・クライアントを開発するためのロードマップ」も参照してください。

Webサービスの非同期呼出しの概要

Webサービスの非同期呼出しをサポートするため、WebLogic Webサービスでは、非同期クライアント・プログラミング・モデルと非同期トランスポートのどちらか一方または両方を使用できます。

表12-1では、非同期クライアント・プログラミング・モデルとトランスポートのタイプの主要な利点、およびWebサービスの非同期呼出しをサポートするために使用できる構成オプションについて説明します。

注意:
2つのportType(非同期操作用に1つとコールバック操作用に1つ)として定義される2つの一方向操作を含む非同期Webサービス用のWSDLを生成する方法は、現在のリリースではサポートされていません。

表12-1 非同期Webサービス呼出しのサポート

タイプ

説明

利点

クライアント・プログラミング・モデル

Webサービス操作の呼出しに使用される呼出しセマンティクスを記述します(同期または非同期)。

Webサービスを同期的に呼び出す場合、呼出し側のクライアント・アプリケーションは、レスポンスが戻るまで待機してから、処理を続行します。レスポンスが即座に戻る場合であれば、このWebサービス呼出しの方法は適切であると考えられます。しかし、リクエストの処理が遅延する可能性があるため、クライアント・アプリケーションによる処理を続行しレスポンスへの対処は後で行うようにします。

Webサービスを非同期的に呼び出すと、クライアントは処理を中断することなく続行でき、非同期レスポンスが返ると通知を受け取ります。

非同期呼出しをサポートするには、clientgen Antタスクを使用して、Webサービス・ポート上で非同期的な種類の操作をそれぞれ自動的に生成します(この後の「非同期Webサービス呼出しのためのクライアント・アーティファクトの作成」で説明しています)。続いて、非同期のレスポンスまたは障害が後で戻されたときにそれを処理するクライアントのメソッド(ビジネス・ロジックを含む)を追加します。最後に、Webサービスを非同期的に呼び出すため、操作を直接呼び出すのではなく、非同期的な種類の操作を呼び出します。たとえば、addNumbersという操作を直接呼び出すのではなく、addNumbersAsyncを呼び出します。

非同期的に呼び出すことで、Webサービス・クライアントは、Webサービスに対するリクエストを開始し、中断することなく処理を続行し、以降のある時点でレスポンスを受け取ることができます。

トランスポート

トランスポートには、非同期クライアント・トランスポート、接続作成トランスポート、同期トランスポートの3種類があります。トランスポートの各タイプの比較については、表12-2を参照してください。

非同期クライアント・トランスポートおよび接続作成トランスポートの主要な利点は次のとおりです。

- ネットワークが停止したときのフォルト・トレランスが向上します。

- サーバーでトラフィックのスパイクをいっそう効果的に緩和できるようになります。

構成

Webサービスの非同期呼出しをサポートするようにWebサービスの永続性とバッファリング(オプション)を構成します。

詳細は、「Webサービスを非同期に呼び出すためのサーバーの構成」を参照してください。

Webサービス機能の構成には、次のような利点があります。

- 永続性は、時間のかかるリクエストをサポートし、途中でサーバーを再起動しても継続できます。

- バッファリングを使用すると、Webサービスに対するすべてのリクエストを非同期に処理できます。

表12-2では、Webサービス・クライアントからのWebサービスの非同期呼出し(または、構成されている場合は同期呼出し)に対してWebLogic Serverがサポートするトランスポートのタイプを示します。

表12-2 Webサービスの非同期呼出しのトランスポート・タイプ

トランスポート・タイプ

説明

非同期クライアント・トランスポート

アドレス可能なクライアント側非同期レスポンス・エンドポイントとWS-Addressingを使用することで、スケーラブルな非同期クライアント・プログラミング・モデルを提供します。

非同期クライアント・トランスポートは、レスポンス・メッセージの配信を、リクエスト・メッセージの送信に使用されるトランスポート・リクエストの開始から切り離します。レスポンス・メッセージは、Webサービスから開始する新しい接続を使用して、非同期レスポンス・エンドポイントに送信されます。クライアントは、WS-Addressingヘッダーを使用して、リクエスト・メッセージとレスポンス・メッセージを関連付けます。

非同期クライアント・トランスポートは、向上したフォルト・トレランスを提供し、サーバー負荷のスパイクをより適切に緩和できるようにします。

非同期クライアント・トランスポートの使用に関する詳細は、「スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)」を参照してください。

非同期クライアント・トランスポートは、次のプログラミング・モデルをサポートします。

- 次のいずれかの方法を使用する非同期およびディスパッチ・コールバック処理。
- 「非同期ハンドラ・インタフェースの開発」で説明されているポートベースの非同期コールバック・ハンドラAsyncClientHandlerFeature。拡張性があり、JVMを再起動しても維持されるため、非同期呼び出しを使用するときのベスト・プラクティスとして使用することをお薦めします。

- 「JAX-WS参照実装の使用」で説明されている、リクエストごとの非同期コールバック・ハンドラ。

- 「JAX-WS参照実装の使用」で説明されている非同期ポーリング。

- 「同期操作のための非同期クライアント・トランスポートの構成」で説明されている、フラグの有効化による同期呼出し。

接続作成トランスポート

Web Services Make Connection 1.1または1.0を使用してファイアウォールの内側からの非同期Webサービス呼出しを可能にします。

接続作成は、非同期クライアント・トランスポートの代わりとなるクライアント・ポーリング・メカニズムです。非同期クライアント・トランスポートと同様に、接続作成を使用するとリクエスト・メッセージの送信に使用されるトランスポート・リクエストの開始から、レスポンス・メッセージを切り離すことができます。ただし、レスポンスを転送するためにアドレス可能な非同期レスポンス・エンドポイントを必要とする非同期クライアント・トランスポートとは異なり、接続作成では、通常、リクエスト・メッセージの送信元はアドレス可能ではなく、着信接続を受け付けることはできません。たとえば、送信元がファイアウォールの内側にあるような場合です。

接続作成トランスポートは、向上したフォルト・トレランスを提供し、サーバー負荷のスパイクをより適切に緩和できるようにします。

接続作成トランスポートの詳細は、「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照してください。

接続作成トランスポートは拡張性があり、JVMを再起動しても維持されるため、ファイアウォールの内側から非同期呼出しを使用するときのベスト・プラクティスとしてお薦めします。次のプログラミング・モデルをサポートします。

- 次のいずれかの方法を使用する非同期およびディスパッチ・コールバック処理。
- 「非同期ハンドラ・インタフェースの開発」で説明されているポートベースの非同期コールバック・ハンドラAsyncClientHandlerFeature。

- 「JAX-WS参照実装の使用」で説明されている、リクエストごとの非同期コールバック・ハンドラ。

- 「JAX-WS参照実装の使用」で説明されている非同期ポーリング。

- 「同期メソッドのトランスポートとしての接続作成の構成」で説明されている、フラグの有効化による同期呼出し。

拡張性があり、JVMを再起動しても維持されるため、非同期呼出しを使用するときのベスト・プラクティスとして、接続作成トランスポートとAsyncClientHandlerFeatureを使用することをお薦めします。

同期トランスポート

WS-Addressingの非常に制限されたサポートで、同期と非同期のWebサービス呼出しをサポートします。詳細は、「JAX-WS参照実装の使用」を参照してください。

同期呼出しを使用するときは、同期トランスポートをお薦めします。ベスト・プラクティスとはみなされませんが、非同期呼出しに使用することもできます。次のプログラミング・モデルをサポートします。

- 「JAX-WS参照実装の使用」で説明されている、標準JAX-WS RIの実装を使用したリクエスト単位での非同期およびディスパッチ・コールバック処理。

- 「JAX-WS参照実装の使用」で説明されている非同期ポーリング。

- 同期呼出し。

非同期でWebサービスを呼び出すための手順

この項では、Webサービスを非同期に呼び出すために必要な手順について説明します。

Antベースの開発環境を設定済であり、かつjwsc Antタスクを実行してWebサービスをデプロイするためのターゲットを追加できる、作業用のbuild.xmlファイルがあることが前提となっています。詳細は、第3章「JAX-WS Webサービスの開発」を参照してください。

表12-3 非同期でWebサービスを呼び出すための手順

#

手順

説明

1

Webサービスの非同期呼出しをサポートするようにWebサービスの永続性を構成します。

Webサービスまたはクライアントでメッセージを処理するために必要なコンテキスト情報を保持するように、WebサービスとクライアントをホストするサーバーでWebサービスの永続性を構成します。詳細は、「非同期Webサービス呼出しのためのサーバーの構成」を参照してください。

注意: 「JAX-WS参照実装の使用」で説明されているように、(手順3で)標準のJAX-WS RI実装と同期トランスポートを使用してWebサービス・クライアントをプログラミングしている場合は、この手順は必要ありません。

2

Webサービス・バッファリングを構成して、リクエストを非同期的に処理するためのWebサービスを有効化します。(オプション)

この手順はオプションです。リクエストを非同期に処理するようにWebサービスを構成するには、Webサービスをホストするサーバーでバッファリングを構成します。バッファリングを使用すると、Webサービスによる非同期処理のためにJMSキューにメッセージを格納できます。詳細は、「非同期Webサービス呼出しのためのサーバーの構成」を参照してください。

3

非同期呼出しに必要なクライアント・アーティファクトを作成します。

サービス・エンドポイント・インタフェースで非同期ポーリング・メソッドおよび非同期コールバック・ハンドラ・メソッドを生成するには、非同期マッピングを可能にする外部バインディング宣言を作成し、クライアントをコンパイルするときにclientgenに引数としてバインディング・ファイルを渡します。「非同期Webサービス呼出しのためのクライアント・アーティファクトの作成」を参照してください。

4

必要なトランスポートとプログラミング・モデルに基づいて、Webサービス・クライアントを実装します。

必要なトランスポートとプログラミング・モデルに応じて、次のいずれかの項を参照してください。

- 非同期クライアント・トランスポート機能を使用します(「スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)」を参照)。(ベスト・プラクティスとして推奨)

- 接続作成を使用してファイアウォールの内側からの非同期アクセスを可能にします。「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照してください。

- 同期トランスポートを使用して、非同期ポーリングやリクエストごとの非同期コールバック処理などの標準JAX-WSプログラミング・モデルを実装します。「JAX-WS参照実装の使用」を参照してください。

クラスタでWebサービスを使用するときは、「非同期Webサービス・メッセージングのクラスタリングに関する考慮事項」で説明されているガイドラインを確認してください。

5

Webサービス・クライアントをコンパイルし、クライアント・アーティファクトのパッケージを作成します。

詳細は、「クライアント・アプリケーションのコンパイルと実行」を参照してください。

6

Webサービス・クライアントをデプロイします。

「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

7

Webサービス・クライアントをモニターします。

WebLogic Server管理コンソールまたはWLSTを使用して、呼出し、エラー、フォルトの数など、Webサービスを非同期に呼び出すクライアントの実行時情報をモニターできます。「非同期Webサービス呼出しのモニタリング」を参照してください。

Webサービスを非同期に呼び出すためのサーバーの構成

注意:
「JAX-WS参照実装の使用」で説明されているように、標準のJAX-WS RI実装と同期トランスポートを使用してWebサービス・クライアントをプログラミングしている場合は、この手順は必要ありません。

Webサービスの非同期呼出しをサポートするには、Webサービスとクライアントをデプロイするサーバーで、次の表で定義されている機能を構成する必要があります。

表12-4 非同期Webサービス呼出しの構成

機能

説明

永続性

Webサービスの永続性は、次の種類の情報を保存するために使用されます。

- クライアントのIDとプロパティ

- ヘッダーと本体を含むSOAPメッセージ

- Webサービスまたはクライアントでメッセージを処理するために必要なコンテキスト・プロパティ(非同期メッセージと同期メッセージの両方)

接続作成トランスポート・プロトコルは、Webサービスの永続性を次のように利用します。

- MCレシーバ(Webサービス)上に構成されたWebサービス永続性は、宛先の接続作成匿名URIに対する着信接続作成メッセージを待機しているレスポンス・メッセージを保持します。メッセージは、着信接続作成メッセージに対するレスポンスとして返されるまで、または永続ストア・オブジェクトの最大存続期間に達してストアから消去されるまで保持されます。

- MCイニシエータ(Webサービス・クライアント)上に構成されたWebサービス永続性は、VM再起動後のリカバリのために非同期クライアント・ハンドラ機能で使用されます。

構成ウィザードでWebサービス固有の拡張テンプレートを使用してWebLogic Serverドメインを拡張することにより、Webサービスの永続性を構成できます。あるいは、Oracle WebLogic Server管理コンソールまたはWLSTを使用して、これらの高度な機能に必要なリソースを構成できます。Webサービス永続性の構成の詳細は、「Webサービス・クライアントのためのWebサービス永続性の構成」を参照してください。クライアントとメッセージの情報の保持に使用できるAPIの詳細は、「レスポンスへのリクエスト・コンテキストの伝播」を参照してください。

メッセージ・バッファリング

バッファ付き操作がクライアントによって呼び出されると、リクエストはJMSキューに格納され、WebLogic Serverはリクエストを非同期に処理します。リクエストがまだキューの中にある間にWebLogic Serverがダウンした場合は、WebLogic Serverが再起動してからすぐにリクエストの処理が行われます。メッセージ・バッファリングは、Webサービスをホストしているサーバー上で構成されます。構成情報の詳細は、第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。

注意: Webサービス・クライアントではメッセージ・バッファリングが自動的に有効になります。

Webサービスを非同期に呼び出すためのクライアント・アーティファクトの構築

WebLogic Serverのクライアント側ツール(clientgenなど)を使用すると、非同期Webサービス呼出しに必要なクライアント・アーティファクトを自動的に生成できます。具体的には、次のアーティファクトが生成されます。

- リクエストごとの非同期コールバック・ハンドラを使用して、または使用しないで、Webサービスを非同期に呼び出すためのサービス・エンドポイント・インタフェース。たとえば、Webサービスで次のようなメソッドが定義されているものとします。

public int addNumbers(int opA, int opB) throws MyException

この場合は、次のようなメソッドが生成されます。

public Future<?> addNumbersAsync(int opA, int opB,
AsyncHandler<AddNumbersResponse>)
public Response<AddNumbersResponse> addNumbersAsync(int opA, int opB)

- ハンドラを実装し、AsyncClientHandlerFeatureを使用してポート上にそのハンドラを設定するための非同期ハンドラ・インタフェース。非同期ハンドラ・インタフェースの名前は、portInterfaceNameAsyncHandlerとなり、ここでportInterfaceNameはポート・インタフェース名を指定します。
たとえば、ポート・タイプ名がAddNumbersPortTypeであるWebサービスの場合、次のメソッドを含むAddNumbersPortTypeAsyncHandlerという名前の非同期ハンドラ・インタフェースが生成されます。

public void onAddNumbersResponse(Response<AddNumbersResponse>)

AsyncClientHandlerFeatureについては、後の「非同期ハンドラ・インタフェースの開発」で説明します。

WSDLのコンパイル時に、サービス・エンドポイント・インタフェースで非同期クライアント・アーティファクトを生成するには、WSDLファイルでjaxws:enableAsyncMappingバインディング宣言を有効にします。

あるいは、特定のWSDLまたはXMLスキーマ・ドキュメントのすべてのバインディング宣言を格納する外部バインディング宣言ファイルを作成できます。次に、バインディング宣言ファイルをwsdlc、jwsc、またはclientgen Antタスクの<binding>子要素に渡します。詳細は、「JAX-WSバインディング宣言を使用した外部バインディング宣言ファイルの作成」を参照してください。

次に示すバインディング宣言ファイル(jaxws-binding.xml)の例では、jaxws:enableAsyncMappingバインディング宣言を有効にしています。

<bindings
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation="AddNumbers.wsdl"
xmlns="http://java.sun.com/xml/ns/jaxws">
<bindings node="wsdl:definitions">
<package name="examples.webservices.async"/>
<enableAsyncMapping>true</enableAsyncMapping>
</bindings>
</bindings>

次に、build.xmlファイルを更新し、Webサービス操作を非同期に呼び出すために必要なクライアント・アーティファクトを生成するため、次の手順を実行します。

1. taskdef Antタスクを使用して、clientgen Antタスクの完全なクラス名を定義します。

2. 前に定義した非同期バインディング宣言が格納されている外部バインディング宣言ファイルへの参照を含むターゲットを追加します。この場合、clientgen Antタスクは、同期的な種類と非同期的な種類のWebサービス操作をJAX-WSスタブ内に生成します。

例:

<taskdef name="clientgen"
classname="weblogic.wsee.tools.anttasks.ClientGenTask" />

<target name="build_client">

<clientgen
type="JAXWS"
wsdl="AddNumbers.wsdl"
destDir="${clientclasses.dir}"
packageName="examples.webservices.async.client">
<binding file="jaxws-binding.xml" />
</clientgen>
<javac
srcdir="${clientclass-dir}" destdir="${clientclass-dir}"
includes="**/*.java"/>
<javac
srcdir="src" destdir="${clientclass-dir}"
includes="examples/webservices/async/client/**/*.java"/>

</target>

スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)

非同期クライアント・トランスポート機能は、スケーラブルな非同期クライアント・プログラミング・モデルを提供します。具体的には、次のような機能があります。

- 図12-1に示すような、クライアント側の非同期レスポンス・エンドポイントを公開します。

- 要求された非同期ハンドラの実装を呼び出すサービスの実装を作成して公開します。

- すべての非一方向アウトバウンド・メッセージに、WS-Addressingの非匿名ReplyToヘッダーを自動的に追加します。このヘッダーは、公開されたレスポンス・エンドポイントを参照します。

- 前記の機能を使用して、非同期リクエストとレスポンス・メッセージを関連付けます。

非同期クライアント・トランスポート機能が有効になっているとき、他のすべてのJAX-WSクライアント・プログラミング・モデル(非同期ポーリング、コールバック・ハンドラ、ディスパッチなど)は引き続きサポートされます。非同期クライアント・トランスポート機能が有効になっているとき、この機能を使用するように明示的に構成されていないと、同期Webサービス操作はデフォルトで同期トランスポートを使用します。

次の図では、非同期クライアント・トランスポート機能が使用するメッセージ・フローを示します。

図12-1 非同期クライアント・トランスポート機能

前の図に示すように、次のような処理が行われます。

1. クライアントは、クライアント・プロキシで非同期クライアント・トランスポート機能を有効にして、非同期Webサービス操作を呼び出します。

2. Webサービス操作がクライアント・プロキシを介して呼び出されます。

3. Webサービスはリクエストを処理し、(その後のどこかの時点で)レスポンス・メッセージをクライアントに返送します。レスポンス・メッセージはクライアントの非同期レスポンス・エンドポイントに送信されます。非同期レスポンス・エンドポイントのアドレスは、WS-Addressingヘッダーに保持されています。

4. レスポンス・メッセージがクライアント・プロキシを介して適切なクライアントに転送されます。

5. レスポンス・メッセージを処理するために、クライアントの非同期ハンドラが呼び出されます。

次の項では、非同期クライアント・トランスポートを使用してスケーラブルな非同期JAX-WSクライアントを開発する方法を説明します。

- 非同期クライアント・トランスポート機能の有効化と構成

- 非同期ハンドラ・インタフェースの開発

- レスポンスへのユーザー定義リクエスト・コンテキストの伝播

非同期クライアント・トランスポート機能の有効化と構成

注意:
接続作成と非同期クライアント・トランスポート機能を一緒に使用することはできません。同じWebサービス・クライアントで両方の機能を有効にしようとすると、エラーが返されます。接続作成の詳細は、「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照してください。

クライアントで非同期クライアント・トランスポート機能を有効にするには、Webサービス・プロキシまたはディスパッチを作成するときにパラメータとしてweblogic.jws.jaxws.client.async.AsyncClientTransportFeatureのインスタンスを渡します。

AsyncClientTransportFeatureによって記述されている非同期レスポンス・エンドポイントは、同じクライアントIDを共有するすべてのクライアント・インスタンスによって使用され、そのクライアントIDを使用する最初のクライアント・インスタンスが公開された時点から有効になります。非同期レスポンス・エンドポイントは、クライアントIDが明示的に破棄されるか、または(たとえば、ホストWebアプリケーションまたはEJBがアンデプロイされて)クライアントのコンテナが非アクティブ化されるまで、発行されたままになります。クライアントIDの管理の詳細は、「クライアントIDの管理」を参照してください。

非同期レスポンス・エンドポイント・アドレスは、次の形式を使用して自動的に生成されます。

http://contextAddress:port/context/targetPort-AsyncResponse

各値の説明は次のとおりです。

- contextAddress:port: 次のいずれかを指定します。

- クラスタ・アプリケーションの場合は、クラスタ・アドレスとポート。

- クラスタ・アプリケーションでない場合は、選択されているプロトコルのデフォルトのWebLogic Serverアドレスとポート。

- デフォルトのアドレスが定義されていない場合は、指定されているプロトコルの最初のネットワーク・チャネル・アドレス。ネットワーク・チャネルの詳細は、『Oracle WebLogic Serverサーバー環境の管理』のネットワーク・リソースの構成に関する項を参照してください。

- context: 既存のコンテキスト内で実行している場合は、現在のサーブレット・コンテキスト。それ以外の場合は、UUIDによって名前を指定され、スコープがアプリケーションに設定された、新しいコンテキスト。

- targetPort-AsyncResponse: クライアントによってアクセスされるサービスのポート名の後に-AsyncResponseを付加したもの。

非同期クライアント・トランスポート機能は、次の項で説明するように構成できます。

- 非同期レスポンス・エンドポイントのアドレスの構成

- 非同期レスポンス・エンドポイントのReplyToヘッダーとFaultToヘッダーの構成

- 非同期レスポンス・エンドポイントのコンテキスト・パスの構成

- 非同期レスポンス・エンドポイントの公開

- 同期操作用の非同期クライアント・トランスポートの構成

AsyncClientTransportFeature()コンストラクタの形式の詳細は、Oracle WebLogic Server Java APIリファレンスを参照してください。

非同期レスポンス・エンドポイントのアドレスの構成

次に示すように、非同期レスポンス・エンドポイントのアドレスは、AsyncClientTransportFeatureに引数として渡すことで構成できます。

String responseAddress = "http://myserver.com:7001/myReliableService/myClientCallback";
AsyncClientTransportFeature asyncFeature = new AsyncClientTransportFeature(responseAddress);
BackendService port = _service.getBackendServicePort(asyncFeature);

指定アドレスは、サーバーまたはクラスタの合法的なアドレスにする必要があります(ネットワーク・チャネルまたはプロキシ・アドレスを含む)。エフェメラル・ポートはサポートされません。指定するコンテキストは、スコープを現在のアプリケーション内に指定されているか、または未使用コンテキストを参照している必要があります。別のデプロイ済アプリケーションにスコープが設定されているコンテキストは参照できません。参照しようとするとエラーがスローされます。

次の表では、非同期レスポンス・エンドポイントのアドレスの構成に使用できるコンストラクタを示します。

表12-5 非同期レスポンス・エンドポイントのアドレスを構成するためのコンストラクタ

コンストラクタ

説明

AsyncClientTransportFeature(java.lang.String address)

非同期レスポンス・エンドポイントのアドレスを構成します。

AsyncClientTransportFeature(java.lang.String address, boolean doPublish)

次のものを構成します。

- 非同期レスポンス・エンドポイントのアドレス。

- 指定したアドレスでエンドポイントを公開するかどうか。詳細は、「非同期レスポンス・エンドポイントの公開」を参照してください。

AsyncClientTransportFeature(java.lang.String address, boolean doPublish, boolean useAsyncWithSyncInvoke)

次のものを構成します。

- 非同期レスポンス・エンドポイントのアドレス。

- 指定したアドレスでエンドポイントを公開するかどうか。詳細は、「非同期レスポンス・エンドポイントの公開」を参照してください。

- 同期操作用に非同期クライアント・トランスポートを有効にするかどうか。詳細は、「同期操作用の非同期クライアント・トランスポートの構成」を参照してください。

非同期レスポンス・エンドポイントのReplyToヘッダーとFaultToヘッダーの構成

非同期レスポンス・エンドポイントのjavax.xml.ws.wsaddressing.W3CEndpointReference型のすべての発信ReplyToおよびFaultToヘッダーに対して使用するアドレスは、AsyncClientTransportFeatureに引数として渡すことで構成できます。

たとえば、ReplyToヘッダー・アドレスのみを構成するには次のようにします。

W3CEndpointReference replyToAddress = "http://myserver.com:7001/myReliableService/myClientCallback";
AsyncClientTransportFeature asyncFeature = new AsyncClientTransportFeature(replyToAddress);
BackendService port = _service.getBackendServicePort(asyncFeature);

ReplyToとFaultToの両方のヘッダー・アドレスを構成するには:

W3CEndpointReference replyToAddress = "http://myserver.com:7001/myReliableService/myClientCallback";
W3CEndpointReference faultToAddress = "http://myserver.com:7001/myReliableService/FaultTo";
AsyncClientTransportFeature asyncFeature = new AsyncClientTransportFeature(replyToAddress, faultToAddress);
BackendService port = _service.getBackendServicePort(asyncFeature);

次の表では、発信ReplyToおよびFaultToヘッダーのエンドポイント参照アドレスの構成に使用できるコンストラクタを示します。

表12-6 ReplyToおよびFaultToヘッダーを構成するためのコンストラクタ

コンストラクタ

説明

AsyncClientTransportFeature(javax.xml.ws.wsaddressing.W3CEndpointReference replyTo)

発信ReplyToヘッダーのエンドポイント参照アドレスを構成します。

AsyncClientTransportFeature(javax.xml.ws.wsaddressing.W3CEndpointReference replyTo, boolean doPublish)

次のものを構成します。

- 発信ReplyToヘッダーのエンドポイント参照アドレス。

- 指定したアドレスでエンドポイントを公開するかどうか。詳細は、「非同期レスポンス・エンドポイントの公開」を参照してください。

AsyncClientTransportFeature(javax.xml.ws.wsaddressing.W3CEndpointReference replyTo, boolean doPublish, boolean useAsyncWithSyncInvoke)

次のものを構成します。

- 発信ReplyToヘッダーのエンドポイント参照アドレス。

- 指定したアドレスでエンドポイントを公開するかどうか。詳細は、「非同期レスポンス・エンドポイントの公開」を参照してください。

- 同期操作用に非同期クライアント・トランスポートを有効にするかどうか。詳細は、「同期操作用の非同期クライアント・トランスポートの構成」を参照してください。

AsyncClientTransportFeature(javax.xml.ws.wsaddressing.W3CEndpointReference replyTo, javax.xml.ws.wsaddressing.W3CEndpointReference faultTo)

発信ReplyToおよびFaultToヘッダーのエンドポイント参照アドレスを構成します。

AsyncClientTransportFeature(javax.xml.ws.wsaddressing.W3CEndpointReference replyTo, javax.xml.ws.wsaddressing.W3CEndpointReference faultTo, boolean doPublish)

次のものを構成します。

- 発信ReplyToおよびFaultToヘッダーのエンドポイント参照アドレス。

- 指定したアドレスでエンドポイントを公開するかどうか。詳細は、「非同期レスポンス・エンドポイントの公開」を参照してください。

AsyncClientTransportFeature(javax.xml.ws.wsaddressing.W3CEndpointReference replyTo, javax.xml.ws.wsaddressing.W3CEndpointReference faultTo, boolean doPublish, boolean useAsyncWithSyncInvoke)

次のものを構成します。

- 発信ReplyToおよびFaultToヘッダーのエンドポイント参照アドレス。

- 指定したアドレスでエンドポイントを公開するかどうか。詳細は、「非同期レスポンス・エンドポイントの公開」を参照してください。

- 同期操作用に非同期クライアント・トランスポートを有効にするかどうか。詳細は、「同期操作用の非同期クライアント・トランスポートの構成」を参照してください。

非同期レスポンス・エンドポイントのコンテキスト・パスの構成

クライアントがサーブレットまたはWebアプリケーション・ベースのWebサービス内で実行している場合、ServletContextとコンテキスト・パスを使用して非同期レスポンス・エンドポイントを構成できます。次のように、AsyncClientTransportFeatureに引数として情報を渡します。

- サーブレット内で実行している場合:

AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(getServletContext());

- WebサービスまたはEJBベースのWebサービス内で実行している場合:

import com.sun.xml.ws.api.server.Container;
...
Container c = ContainerResolver.getInstance().getContainer();
ServletContext servletContext = c.getSPI(ServletContext.class);
AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(servletContext);

指定するコンテキストは、スコープを現在のアプリケーション内に指定されているか、または未使用コンテキストを参照している必要があります。別のデプロイ済みアプリケーションにスコープが設定されているコンテキストは参照できません。

注意:
AsyncClientTransportFeatureに対して空のコンストラクタを使用すると、Webサービスのランタイムは現在の機能がインスタンス化されたコンテナの検出を試み、使用可能なコンテナ・コンテキストを使用してエンドポイントを公開します。

次の表では、非同期レスポンス・エンドポイントのコンテキスト・パスの構成に使用できるコンストラクタを示します。

表12-7 非同期レスポンス・エンドポイントのコンテキスト・パスを構成するためのコンストラクタ

コンストラクタ

説明

AsyncClientTransportFeature(java.lang.Object context)

非同期レスポンス・エンドポイントのコンテキスト・パスを構成します。

AsyncClientTransportFeature(java.lang.Object context, boolean useAsyncWithSyncInvoke)

次のものを構成します。

- 非同期レスポンス・エンドポイントのコンテキスト・パス。

- 同期操作用に非同期クライアント・トランスポートを有効にするかどうか。詳細は、「同期操作用の非同期クライアント・トランスポートの構成」を参照してください。

非同期レスポンス・エンドポイントの公開

次のプロパティを構成するときにdoPublishブール値をAsycnClientTransportFeature()に引数として渡すことで、非同期レスポンス・エンドポイントを公開するかどうかを構成できます。

- 非同期レスポンス・エンドポイントのアドレス。表12-5を参照してください。

- ReplyToおよびFaultToヘッダー。表12-6を参照してください。

- 非同期レスポンス・エンドポイントのコンテキスト・パス。表12-7を参照してください。

doPublishをfalseに設定した場合は、非同期レスポンス・エンドポイントは自動的に発行されませんが、WS-Addressingヘッダーがアウトバウンドの非一方向メッセージに追加されます。このシナリオは次のプログラミング・モデルをサポートします。

- 非同期ポーリング(Responseオブジェクトへのアクセスは試みられません)

- ディスパッチ非同期ポーリング(Responseオブジェクトへのアクセスは試みられません)

- ディスパッチ一方向呼出し

- 同期トランスポート・オプションを使用する同期呼出し(デフォルト)

他のすべての非同期プログラミング・モデルについては、非同期レスポンス・エンドポイントが使用できる必要があり、doPublishがfalseに設定されている場合は、Webサービス・クライアントはアウトバウンド・リクエストを行う前にエンドポイントを公開する必要があります。

次の例では、非同期レスポンス・エンドポイント・アドレスを構成し、非同期レスポンス・エンドポイントを公開します。

String responseAddress = "http://localhost:7001/myReliableService/myReliableResponseEndpoint";
boolean doPublish = true;
AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(responseAddress, doPublish);
BackendService port = _service.getBackendServicePort(asyncFeature);

同期操作用の非同期クライアント・トランスポートの構成

次のプロパティを構成するときに、useAsyncWithSyncInvokeブール・フラグを使用して、同期操作用の非同期クライアント・トランスポートを有効または無効にできます。

- 非同期レスポンス・エンドポイントのアドレス。表12-5を参照してください。

- ReplyToおよびFaultToヘッダー。表12-6を参照してください。

- 非同期レスポンス・エンドポイントのコンテキスト・パス。表12-7を参照してください。

次の例では、非同期レスポンス・エンドポイント・アドレスを構成し、同期操作に対して非同期クライアント・トランスポートを使用できるようにします。

String responseAddress = "http://localhost:7001/myReliableService/myReliableResponseEndpoint";
boolean useAsyncWithSyncInvoke = true;
AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(responseAddress, useAsyncWithSyncInvoke);
BackendService port = _service.getBackendServicePort(asyncFeature);

非同期ハンドラ・インタフェースの開発

注意:
この項で説明するように単一の非同期ハンドラ・インスタンスをポートに設定した後、「JAX-WS参照実装の使用」で説明されているようにリクエスト単位の非同期ハンドラの構成を試みると、実行時例外が返されます。

「Webサービスを非同期に呼び出すためのクライアント・アーティファクトの構築」で説明されているように、非同期ハンドラ・インタフェースweblogic.jws.jaxws.client.async.AsyncClientHandlerFeatureは、リクエスト単位ベースではなく、ポートに単一の非同期ハンドラ・インスタンスを設定します。

たとえば、「Webサービスを非同期に呼び出すためのクライアント・アーティファクトの構築」で説明されているようにclientgenを使用してクライアント・クラスを構築するときは、次に示すように、非同期ハンドラ・インタフェースが生成されます。

例12-1 非同期ハンドラ・インタフェースの例

import javax.xml.ws.Response;

/**
* This class was generated by the JAX-WS RI.
* Oracle JAX-WS 2.1.5
* Generated source version: 2.1
*
*/
public interface BackendServiceAsyncHandler {

/**
*
* @param response
*/
public void onDoSomethingResponse(Response<DoSomethingResponse> response);

}

非同期ハンドラ・インタフェースは、ポート・インタフェースと同じパッケージの一部として生成され、サービスで定義されている操作に対するレスポンスを受け取るために必要なメソッドを表します。クライアントのコードでこのインタフェースをインポートして実装し、厳格に型指定された方法で非同期レスポンスを受信して処理する手段を提供できます。

ポートに単一の非同期ハンドラ・インスタンスを設定するには、Webサービス・プロキシまたはディスパッチを作成するときに、パラメータとしてweblogic.jws.jaxws.client.async.AsyncClientHandlerFeatureのインスタンスを渡します。レスポンス・メッセージを受信したときに呼び出される非同期ハンドラの名前を指定します。

次の例では、非同期ハンドラ・インタフェースの開発方法を示します。この例を見ると、AsyncClientHandlerFeatureを初期化し、バックエンド・サービスで呼出しを行うために使用されるポートに非同期ハンドラの実装を接続する方法がわかります。この例は、例11-1「非同期Webサービス・クライアントのベスト・プラクティスの例」からの抜粋です。

例12-2 非同期ハンドラ・インタフェースの開発の例

import weblogic.jws.jaxws.client.async.AsyncClientHandlerFeature;
...
BackendServiceAsyncHandler handler = new BackendServiceAsyncHandler() {
public void onDoSomethingResponse(Response<DoSomethingResponse> res) {
// ... Handle Response ...
try {
DoSomethingResponse response = res.get();
_lastResponse = response.getReturn();
System.out.println("Got async response: " + _lastResponse);
} catch (Exception e) {
_lastResponse = e.toString();
e.printStackTrace();
}
}
};
AsyncClientHandlerFeature handlerFeature = new AsyncClientHandlerFeature(handler);
features.add(handlerFeature);
_features = features.toArray(new WebServiceFeature[features.size()]);
BackendService anotherPort = _service.getBackendServicePort(_features);
...
// Make the invocation. Our asynchronous handler implementation (set
// into the AsyncClientHandlerFeature above) receives the response.
String request = "Dance and sing";
System.out.println("Invoking DoSomething asynchronously with request: " + request);
anotherPort.doSomethingAsync(request);

レスポンスへのユーザー定義リクエスト・コンテキストの伝播

weblogic.wsee.jaxws.JAXWSProperties APIで定義されている次のプロパティを使用すると、非同期ハンドラ・インスタンスの状態に依存することなく、ユーザー定義のリクエスト・コンテキスト情報をレスポンス・メッセージに伝播できます。

非同期ハンドラ・インスタンスはいつでも作成される可能性があります(たとえば、クライアントのサーバーがダウンして再起動されるとき)。したがって、非同期ハンドラ・インタフェースにリクエスト・コンテキストを格納しても役に立ちません。

次の表では、JAXWSPropertiesのプロパティを定義します。

表12-8 JAXWSProperties APIによってサポートされるプロパティ

プロパティ

指定内容

MESSAGE_ID

リクエストのメッセージID。クライアントでは、リクエスト・コンテキストにこのプロパティを設定し、リクエストごとのメッセージIDヘッダーの自動生成をオーバーライドできます。

PERSISTENT_CONTEXT

クライアントまたは通信チャネルで必要なコンテキスト・プロパティ。Webサービス・クライアントでは、コンテキスト・プロパティがシリアライズ可能である場合、リクエスト・メッセージに対してコンテキスト・プロパティを保持できます。これらのプロパティは、非同期ハンドラが呼び出されるときに、Responseオブジェクトから使用可能なレスポンス・コンテキスト・マップで使用できます。詳細は、「レスポンスへのリクエスト・コンテキストの伝播」を参照してください。

RELATES_TO

レスポンスが関連付けられているメッセージID。

REQUEST_TIMEOUT

非同期クライアント・トランスポートを使用する同期操作の場合、ブロックしてレスポンスを待機する最大時間。このプロパティのデフォルトは0で、タイムアウトしないことを示します。

さらに、Webサービス・クライアントでは、コンテキスト・プロパティがシリアライズ可能である場合、リクエスト・メッセージに対してコンテキスト・プロパティを保持できます。コンテキスト・プロパティは、クライアントまたは通信チャネルで必要な情報を格納できます。メッセージのプロパティは、weblogic.wsee.jaxws.JAXWSProperties.PERSISTENT_CONTEXTマップ・プロパティの一部として格納し、レスポンス・メッセージが返された後で取得できます。詳細は、「レスポンスへのリクエスト・コンテキストの伝播」を参照してください。

ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)

Webサービスの接続作成は、非同期クライアント・トランスポートの代わりとなるクライアント・ポーリング・メカニズムであり、通常はファイアウォールの内側にあるクライアントのサポートを提供します。http://docs.oasis-open.org/ws-rx/wsmc/200702の接続作成仕様で説明されているように、WebLogic ServerはWS-MakeConnectionバージョン1.1をサポートし、バージョン1.0と後方互換性があります。

接続作成の具体的な機能は次のとおりです。

- リクエスト・メッセージの送信に使用された開始トランスポート・リクエストから、レスポンス・メッセージを切り離すことができるようにします(非同期クライアント・トランスポートと似ています)。

- アドレス可能ではなく着信接続を受け付けることができないWebサービス・クライアントをサポートします(たとえば、ファイアウォールの内側のクライアント)。

- WS-MakeConnectionの仕様で定義されているように、Webサービス・クライアントがMC-Initiatorとして機能し、WebサービスがMC-Receiverとして機能できるようにします。

Webサービスの接続作成の仕様から抜粋した次の図では、標準的な接続作成のメッセージ・フローが示されています。

図12-2 接続作成のメッセージ・フロー

前の図で示されているように、接続作成のメッセージ・フローは次のようになります。

1. getQuote()リクエスト・メッセージが、Webサービス・クライアント(MCイニシエータ)からWebサービス(MCレシーバ)に送信されます。ReplyToヘッダーには、MCイニシエータのUUIDを指定する接続作成の匿名URIが含まれます。
MCレシーバがgetQuote()メッセージを受信します。ReplyToヘッダーに接続作成匿名URIが含まれる場合はレスポンス・メッセージを接続の戻りチャネルで返送できることを示し、ない場合はクライアントが接続作成ポーリングを使用してレスポンス・メッセージを取得します。

2. MCレシーバは、空のレスポンス(HTTP 202)をMCイニシエータに返送することで接続を閉じます。
空のレスポンスを受信すると、MCイニシエータはポーリング・メカニズムを初期化して開始し、以降のポーリングをMCレシーバに送信できるようにします。具体的には、MCイニシエータのポーリング・メカニズムは、連続するポーリング間の時間に対して構成されている間隔に有効期限が設定されたタイマーを開始します。

3. タイマーが切れると、MCイニシエータは、同じ接続作成匿名URI情報を格納した接続作成メッセージをMCレシーバに送信します。

4. MCレシーバはgetQuote()操作の処理を完了していないので、MCイニシエータに返送できるレスポンスはありません。その結果、MCレシーバは、再び空のレスポンス(HTTP 202)を返送することで現時点では送信できるレスポンスがないことを示し、接続を閉じます。
空のメッセージを受信すると、MCイニシエータは接続作成ポーリング・メカニズムのタイマーを再起動します。

タイマーが切れる前に、getQuote()操作が完了します。元のリクエストのReplyToヘッダーには接続作成匿名URIが含まれていたので、MCレシーバはレスポンスを格納し、アドレスが一致する次の接続作成メッセージの受信を待ちます。

5. タイマーが切れると、MCイニシエータは、同じ接続作成匿名URI情報を格納した接続作成メッセージをMCレシーバに送信します。

6. 接続作成メッセージを受信すると、MCレシーバは格納されているレスポンス・メッセージを取得し、受信した接続作成メッセージに対するレスポンスとして送信します。
MCイニシエータはレスポンス・メッセージを受信し、接続作成ポーリング・メカニズムを終了します。

ファイアウォールの内側から非同期呼出しを使用するときは、接続作成トランスポートを使用することをお薦めします。サポートされるプログラミング・モデルの一覧については、表12-2「Webサービスの非同期呼出しのトランスポート・タイプ」を参照してください。

次の項では、Webサービスとクライアントで接続作成を有効にして構成する方法を説明します。

- Webサービスでの接続作成の有効化と構成

- Webサービス・クライアントでの接続作成の有効化と構成

Webサービスでの接続作成の有効化と構成

接続作成を有効にするには、接続作成ポリシー・アサーションをWebサービスにアタッチした後、標準のJAX-WSクライアントAPIを使用してクライアントからそのメソッドを呼び出します。ポリシーをWebサービスにアタッチするには、次のいずれかの方法を使用します。

- @PolicyアノテーションをJWSファイルに追加します。接続作成ポリシーをアタッチできるのはクラス・レベルだけです。

- ポリシーに対する参照をWebサービスのWSDLに追加します。

次の項では、Webサービスで接続作成を有効にするために必要な手順を説明します。

- Webサービスの接続作成WS-Policyファイルの作成(オプション)

- 接続作成を有効にするためのJWSファイルのプログラミング

Webサービスの接続作成WS-Policyファイルの作成(オプション)

WS-Policyファイルは、WS-Policy仕様に準拠するポリシー・アサーションを含むXMLファイルです。この場合、WS-PolicyファイルにはWebサービスの接続作成のポリシー・アサーションが含まれています。

WebLogic Serverには、標準的な接続作成アサーションを含むWS-Policyファイルがあらかじめパッケージ化されているので、独自のWS-Policyファイルを作成しない場合は、このファイルを使用できます。次の表に、接続作成をサポートするあらかじめパッケージ化されているWS-Policyファイルを示します。場合によっては、ポリシーによって信頼性のあるメッセージングと接続作成の両方が有効化されます。詳細は、付録A「Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」を参照してください。

注意:
接続作成ポリシーをアタッチできるのはクラス・レベルのみです。メソッド・レベルで接続作成ポリシーをアタッチすることはできません。

表12-9 あらかじめパッケージ化されていて接続作成をサポートするWS-Policyファイル

あらかじめパッケージ化されているWS-Policyファイル

説明

Mc1.1.xml

Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。WS-Policy 1.5プロトコルが使用されます。「Mc1.1.xml (WS-Policyファイル)」を参照してください。

Mc.xml

Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。WS-Policy 1.2プロトコルが使用されます。「Mc.xml (WS-Policyファイル)」を参照してください。

Reliability1.2_ExactlyOnce_WithMC1.1.xml

サービス品質に関するポリシー・アサーションを指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。「Reliability1.2_ExactlyOnce_WithMC1.1.xml (WS-Policyファイル)」を参照してください。

Reliability1.2_SequenceSTR.xml

信頼性のあるシーケンスでメッセージを保護するために、CreateSequenceメッセージで参照されるwsse:SecurityTokenReferenceをランタイムが使用するように指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。「Reliability1.2_SequenceSTR.xml (WS-Policyファイル)」を参照してください。

Reliability1.0_1.2.xml

1.2と1.0のWS-Reliableメッセージング・ポリシー・アサーションを結合します。1.2バージョンのポリシー・アサーションはWebサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。このサンプルは、適切なポリシーの選択に基づいて実行時に適用されるポリシー・アサーションを決定します。「Reliability1.0_1.2.xml (WS-Policyファイル)」を参照してください。

WebLogic Serverに含まれる、あらかじめパッケージ化されているMake Connection WS-Policyファイルの1つを使用できます。これらのファイルは、ほとんどのユースケースに適合しています。あらかじめパッケージ化されているファイルは変更できません。値がニーズを満たさない場合は、カスタムのWS-Policyファイルを作成する必要があります。たとえば、Webサービスのクライアント側で必要に応じてMake Connectionのサポートを構成できます。Make Connectionポリシー・アサーションは、WS-PolicyAssertions仕様に準拠しています。

接続作成アサーションを含むカスタムWS-Policyファイルを作成するには、次のガイドラインを使用してください。

- WS-Policyファイルのルート要素は、常に<wsp:Policy>です。

- Webサービスの接続作成を構成するには、<wsmc:MCSupported>子要素を追加して、Webサービスの接続作成のサポートを定義します。

- <wsmc:MCSupported>子要素は、1つのポリシー属性Optionalを含み、接続作成をWebサービス・クライアントで構成する必要があるかどうかを指定します。この属性はtrueまたはfalseに設定でき、デフォルトではtrueに設定されます。falseに設定した場合は、接続作成の使用は必須であり、ReplyToヘッダーとFaultToヘッダー(指定する場合)の両方に接続作成匿名URIが含まれる必要があります。

次の例では、Webサービスで接続作成を有効にし、Webサービス・クライアントで接続作成を有効にする必要があることを指定しています。この例では、WS-Policy 1.5プロトコルを使用しています。

<?xml version="1.0"?>
<wsp15:Policy  xmlns:wsp15="http://www.w3.org/ns/ws-policy"
xmlns:wsmc="http://docs.oasis-open.org/ws-rx/wsmc/200702">
<wsmc:MCSupported wsp15:Optional="false" />
</wsp15:Policy>

接続作成を有効にするためのJWSファイルのプログラミング

この項では、あらかじめパッケージ化されている接続作成WS-Policyファイルまたはカスタム接続作成WS-Policyファイルを使用して、Webサービスで接続作成を有効にする方法を説明します。カスタム・ポリシー・ファイルの作成の詳細は、「Webサービスの接続作成WS-Policyファイルの作成(オプション)」を参照してください。

接続作成アサーションが含まれるWS-PolicyファイルをWebサービスに追加するよう指定するには、JWSファイルで@Policyアノテーションを使用します。WebLogic Serverでは、あらかじめパッケージ化されているWS-Policyファイルのセットが提供されます。付録A「Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」を参照してください。

Webサービスの信頼性のあるメッセージングで@Policyアノテーションを使用する場合は、次のガイドラインを参照してください。

- 接続作成ポリシーをアタッチできるのはクラス・レベルのみです。メソッド・レベルで接続作成ポリシーをアタッチすることはできません。

- uri属性を使用して、ポリシー・ファイルのビルド時の場所を以下のように指定します。

- 独自のWS-Policyファイルを作成した場合は、JWSファイルを基準として相対的に場所を指定します。例:

@Policy(uri="McPolicy.xml", attachToWsdl=true)

この例では、McPolicy.xmlファイルはJWSファイルと同じディレクトリに置かれています。

- あらかじめパッケージ化されているWS-Policyファイルの1つか、共有Java EEライブラリにパッケージ化されているWS-Policyファイルを指定するには、そのポリシー・ファイルの名前とパスとともにpolicy:接頭辞を使用します。この構文ではビルド時のjwsc Antタスクに、ファイル・システムの実際のファイルを探させず、Webサービスが、サービスのデプロイ時にWebLogic ServerからWS-Policyファイルを取得することを通知しています。

注意:
共有Java EEライブラリは、様々なエンタープライズ・アプリケーション内にパッケージ化されている複数のWebサービスとWS-Policyファイルを共有する場合に有用です。WS-Policyファイルが共有Java EEライブラリのMETA-INF/policiesまたはWEB-INF/policiesディレクトリに置かれているかぎり、ポリシー・ファイルはWebサービスの同じアーカイブにパッケージ化されている場合と同様に指定できます。ライブラリの作成、およびWebサービスがポリシー・ファイルを見つけることができるようにするための環境設定については、『Oracle WebLogic Serverアプリケーションの開発』の共有Java EEライブラリおよびオプション・パッケージの作成に関する項を参照してください。

- ポリシー・ファイルをWeb上で公開するよう指定するには、次の例に示すとおり、URLと共にhttp:接頭辞を使用します。

@Policy(uri="http://someSite.com/policies/mypolicy.xml"
attachToWsdl=true)

- @PolicyアノテーションのattachToWsdl属性を設定して、ポリシー・ファイルをWebサービスのパブリック規約が記述されたWSDLファイルに付加するかどうかを指定できます。通常は、クライアント・アプリケーションでWebサービスの信頼性のあるメッセージング機能が認識されるよう、パブリックなものとしてポリシーを公開します。そのため、この属性のデフォルト値はtrueです。

@Policyアノテーションの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のweblogic.jws.Policyに関する項を参照してください。

次の例では、接続作成を有効にする簡単なJWSファイルを示します。太字で示されたJavaコードに対応するコーディングのガイドラインについては、例の後の説明を参照してください。

package examples.webservices.async

import javax.jws.WebMethod;
import javax.jws.WebService;
import weblogic.jws.Policy;

/**
* Simple reliable Web Service.
*/

@WebService(name="HelloWorldPortType",
serviceName="HelloWorldService")

@Policy(uri="McPolicy.xml", attachToWsdl=true)
public class HelloWorldImpl {
private static String onewaySavedInput = null;

/**
* A one-way helloWorld method that saves the given string for later
* concatenation to the end of the message passed into helloWorldReturn.
*/
@WebMethod()
public void helloWorld(String input) {
System.out.println(" Hello World " + input);
onewaySavedInput = input;
}

/**
* This echo method concatenates the saved message from helloWorld
* onto the end of the provided message, and returns it.
*/
@WebMethod()
public String echo(String input2) {
System.out.println(" Hello World " + input2 + onewaySavedInput);
return input + onewaySavedInput;
}
}

前のサンプルでは、カスタムMcPolicy.xmlポリシー・ファイルがクラス・レベルでWebサービスにアタッチされています。つまり、ポリシー・ファイルはWebサービスのすべてのパブリック操作に適用されます。接続作成ポリシーをアタッチできるのはクラス・レベルのみです。メソッド・レベルで接続作成ポリシーをアタッチすることはできません。

ポリシー・ファイルはWSDLファイルにアタッチされます。使用可能なあらかじめパッケージ化されているポリシーと、カスタム・ポリシーの作成の詳細は、「Webサービスの接続作成WS-Policyファイルの作成(オプション)」を参照してください。

echo()メソッドは、@WebMethodJWSアノテーションでマークされています。これは、このメソッドがechoというパブリック操作であるということです。@Policyアノテーションがあるために、この操作では接続作成トランスポート・プロトコルが使用されます。

Webサービス・クライアントでの接続作成の有効化と構成

注意:
接続作成と非同期クライアント・トランスポート機能を一緒に使用することはできません。同じWebサービス・クライアントで両方の機能を有効にしようとすると、エラーが返されます。非同期クライアント・トランスポートの詳細は、「スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)」を参照してください。
非同期コールバック・ハンドラ・プログラミング・モデルを使用するときは、非同期ハンドラ機能AsyncClientHandlerFeatureを使用することをお薦めします。詳細は、「非同期ハンドラ・インタフェースの開発」を参照してください。

Webサービス・クライアントで接続作成を有効にするには、Webサービス・プロキシまたはディスパッチを作成するときにパラメータとしてweblogic.wsee.mc.api.McFeatureのインスタンスを渡します。接続作成を有効にする方法の簡単な例を次に示します。

注意:
この例では、同期メソッドに同期トランスポートを使用します。同期メソッドのトランスポートとして接続作成を構成する方法は、「同期メソッドのトランスポートとしての接続作成の構成」を参照してください。

package examples.webservices.myservice.client;

import weblogic.wsee.mc.api.McFeature;
...
List<WebServiceFeature> features = new ArrayList<WebServiceFeature>();
...
McFeature mcFeature = new McFeature();
features.add(mcFeature);
...
// ... Implement asynchronous handler interface as described in
//  Developing the Asynchronous Handler Interface.
// ....
AsyncClientHandlerFeature handlerFeature = new AsyncClientHandlerFeature(handler);
features.add(handlerFeature);
_features = features.toArray(new WebServiceFeature[features.size()]);
BackendService port = _service.getBackendServicePort(_features);
...
// Make the invocation. Our asynchronous handler implementation (set
// into the AsyncClientHandlerFeature above) receives the response.
String request = "Dance and sing";
System.out.println("Invoking DoSomething asynchronously with request: " + request);
anotherPort.doSomethingAsync(request);
..
}
}

次の項では、Webサービス・クライアントで接続作成の特定の機能を構成する方法を説明します。

- 接続作成メッセージ送信の有効時間の構成

- ポーリング間隔の構成

- 指数関数的バックオフの構成

- 同期メソッドのトランスポートとしての接続作成の構成

接続作成メッセージ送信の有効時間の構成

表12-10では、MCイニシエータがMCレシーバへの接続作成メッセージの送信を停止するまでの最大時間を構成するためのMcFeatureメソッドについて説明します。

表12-10 接続作成メッセージ送信の有効時間を構成するためのメソッド

メソッド

説明

String getsExpires()

現在構成されている有効期限の値を返します。

void setExpires(String expires)

有効期限を設定します。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP1D (1日)です。

ポーリング間隔の構成

表12-11では、空のレスポンス・メッセージを受信した後でMCイニシエータがMCレシーバに接続作成メッセージを送信するまでに経過する必要のある時間を構成するためのMcFeatureメソッドについて説明します。指定されている時間内にMCイニシエータが特定のメッセージに対する空ではないレスポンスを受信しない場合、MCイニシエータは別の接続作成メッセージを送信します。

表12-11 ポーリング間隔を構成するためのメソッド

メソッド

説明

String getInterval()

ポーリング間隔を取得します。

void setInterval(String pollingInterval)

ポーリング間隔を設定します。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP0DT5S (5秒)です。

次の例では、ポーリング間隔を36時間に設定しています。

...
McFeature mcFeature = new McFeature();
mcFeature.setInterval("P0DT36H")
MyService port = service.getMyServicePort(mcFeature);
...

指数関数的バックオフの構成

表12-12では、指数関数的バックオフ・フラグを構成するためのMcFeatureメソッドについて説明します。このフラグは、「ポーリング間隔の構成」で説明されているポーリング間隔を、指数関数的バックオフ・アルゴリズムを使用して調整するかどうかを指定します。ポーリング間隔で指定されている時間が経過してもMCイニシエータが空ではないレスポンスを受信しない場合、指数関数的バックオフ・アルゴリズムを使用して、MCイニシエータがレスポンスを受信しないときの連続する再送信のタイミングが設定されます。

指数関数的バックオフ・アルゴリズムは、ポーリングの間隔が、ポーリング間隔を基に指数的に増えるように指定します。たとえば、ポーリング間隔が2秒で、指数関数的バックオフ要素が設定されている場合、レスポンスを受信しない場合の連続ポーリングの間隔は、2、4、8、16、32というように増えていきます。

デフォルト値はfalseであり、連続するポーリングの間隔は指数的に増えず、同じ値が維持されます。

表12-12 指数関数的バックオフを構成するためのメソッド

メソッド

説明

boolean isExponentialBackoff()

指数関数的バックオフが有効かどうかを示すブール値を返します。

void setExponentialBackoff(boolean backoff)

指数関数的バックオフ・フラグを設定します。有効な値は、trueおよびfalseです。デフォルトはfalseです。

次の例では、指数関数的バックオフ・フラグを有効にしています。

...
McFeature mcFeature = new McFeature();
mcFeature.setMessageInterval(P0DT36H)
mcFeature.setExponentialBackoff(true);
MyService port = service.getMyServicePort(mcFeature);
...

同期メソッドのトランスポートとしての接続作成の構成

デフォルトでは、クライアントで接続作成が有効であっても、同期メソッドは同期トランスポートを使用します。同期メソッドのトランスポートとして接続作成を使用するように、クライアントを構成できます。この場合、空ではないレスポンス・メッセージを受信するまで、構成されているポーリング間隔(「ポーリング間隔の構成」を参照)に基づいて、MCイニシエータは接続作成メッセージを送信します。

同期メソッドに使用するトランスポート・プロトコルとして接続作成を構成するには、次のいずれかのメソッドを使用します。

- 新しいMcFeature()オブジェクトをインスタンス化するとき、同期メソッドのトランスポート・プロトコルとして接続作成を使用するかどうかを指定するブール値を、パラメータとして渡すことができます。例:

...
McFeature mcFeature = new McFeature(true);
MyService port = service.getMyServicePort(mcFeature);
...

- 表12-13で示されているMcFeatureメソッドを使用します。例:

...
McFeature mcFeature = new McFeature();
mcFeature.setUseMCWithSyncInvoke(true);
MyService port = service.getMyServicePort(mcFeature);
...

表12-13 同期メソッドのサポートを構成するためのメソッド

メソッド

説明

boolean isUseMCWithSyncInvoke()

同期メソッドのサポートが有効かどうかを示すブール値を返します。

void setUseMCWithSyncInvoke(boolean useMCWithSyncInvoke)

同期メソッド・サポート・フラグを設定します。有効な値は、trueおよびfalseです。デフォルトはfalseです。

weblogic.wsee.jaxws.JAXWSProperties.REQUEST_TIMEOUTプロパティを使用すると、同期メソッドがブロックしてレスポンスを待機する最大時間を設定できます。このプロパティのデフォルトは0で、タイムアウトしないことを示します。メッセージ・プロパティの設定の詳細は、「レスポンスへのユーザー定義リクエスト・コンテキストの伝播」を参照してください。

JAX-WS参照実装の使用

JAX-WS参照実装(RI)は、次のプログラミング・モデルをサポートします。

- java.util.concurrent.Futureインタフェースを使用する非同期クライアント・ポーリング。

- リクエスト単位の非同期コールバック・ハンドラ。呼出し元のクライアントが、呼出し時にコールバック・ハンドラを指定します。レスポンスが使用できるときは、レスポンスを処理するためにコールバック・ハンドラが呼び出されます。

非同期クライアント・トランスポート機能とは異なり、JAX-WS RIはWS-Addressingに対する非常に制限されたサポートを提供します。次のものが含まれます。

- クライアント側アウトバウンドWS-Addressingヘッダーの追加の手動サポート。

- レスポンスを受信するためのクライアント側エンドポイントの公開の手動サポート。

- 正しくないクライアント側プログラミング・モデルの検出はサポートしません(たとえば、同期呼出しはハングします)。

- クライアント側またはサービス側の再起動時の情報の保持はサポートしません。

次に示すサンプル・クライアント・ファイルAsyncClientには、AddNumbersServiceサービスのAddNumbersAsyncメソッドを非同期的に呼び出すAddNumbersTestDriveというメソッドが定義されています。太字で示したJavaコードについては後ほど説明します。

package examples.webservices.async.client;

import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit;

import javax.xml.ws.BindingProvider;

import java.util.concurrent.Future;
import javax.xml.ws.AsyncHandler;
import javax.xml.ws.Response;

public class AsyncClient  {

private AddNumbersPortType port = null;
protected void setUp() throws Exception {
AddNumbersService service = new AddNumbersService();
port = service.getAddNumbersPort();
String serverURI = System.getProperty("wls-server");
((BindingProvider) port).getRequestContext().put(
BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://" + serverURI + "/JAXWS_ASYNC/AddNumbersService");
}

/**
*
* Asynchronous callback handler
*/
class AddNumbersCallbackHandler implements AsyncHandler<AddNumbersResponse> {
private AddNumbersResponse output;
public void handleResponse(Response<AddNumbersResponse> response) {
try {
output = response.get();
} catch (ExecutionException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
AddNumbersResponse getResponse() {
return output;
}
}

public void AddNumbersTestDrive() throws Exception {
int number1 = 10;
int number2 = 20;

// Asynchronous Callback method
AddNumbersCallbackHandler callbackHandler =
new AddNumbersCallbackHandler();
Future<?> resp = port.addNumbersAsync(number1, number2,
callbackHandler);
// For the purposes of a test, block until the async call completes
resp.get(5L, TimeUnit.MINUTES);
int result = callbackHandler.getResponse().getReturn();

// Polling method
Response<AddNumbersResponse> addNumbersResp =
port.AddNumbersAsync(number1, number2);
while (!addNumbersResp.isDone()) {
Thread.sleep(100);
}
AddNumbersResponse reply = addNumbersResp.get();
System.out.println("Server responded through polling with: " +
reply.getResponseType());
}
}

次の例では、非同期ポーリングと非同期コールバック・ハンドラの両方のプログラミング・モデルを実装する手順を示します。

非同期コールバック・ハンドラを実装するには:

1. javax.xml.ws.AsyncHandler<T>インタフェースを実装する非同期ハンドラを作成します。(http://docs.oracle.com/javaee/6/api/javax/xml/ws/AsyncHandler.htmlを参照)。この非同期ハンドラには、handleResponseメソッドを定義します。このメソッドにより、非同期的に呼び出されるサービス・エンドポイント操作の完了時に、クライアントがコールバック通知を受信することが可能になります。タイプはAddNumberResponseに設定する必要があります。

class AddNumbersCallbackHandler implements AsyncHandler<AddNumbersResponse> {
private AddNumbersResponse output;

public void handleResponse(Response<AddNumbersResponse> response) {
try {
output = response.get();
} catch (ExecutionException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();

}
}

AddNumbersResponse getResponse() {
return output;
}
}

2. 非同期コールバック・ハンドラをインスタンス化します。

AddNumbersCallbackHandler callbackHandler =
new AddNumbersCallbackHandler();

3. AddNumbersService Webサービスをインスタンス化し、非同期バージョンのWebサービス・メソッドaddNumbersAsyncを呼び出して非同期コールバック・ハンドラにハンドルを渡します。

AddNumbersService service = new AddNumbersService();
port = service.getAddNumbersPort();
...

Future<?> resp = port.addNumbersAsync(number1, number2,
callbackHandler);

java.util.concurrent.Futureは、(http://docs.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/Future.htmlを参照)非同期計算の結果を表現し、非同期タスクのステータスの確認、結果の取得、タスクの実行のキャンセルを可能にします。

4. 非同期計算の結果を取得します。このサンプルでは、計算の完了を待機するためのタイムアウト値を指定しています。

resp.get(5L, TimeUnit.MINUTES);

5. コールバック・ハンドラを使用してレスポンス・メッセージにアクセスします。

int result = callbackHandler.getResponse().getReturn();

非同期ポーリング・メカニズムを実装するには:

1. AddNumbersService Webサービスをインスタンス化し、非同期バージョンのWebサービス・メソッドaddNumbersAsyncを呼び出します。

Response<AddNumbersResponse> addNumbersResp =
port.AddNumbersAsync(number1, number2);

2. メッセージを受信するまでスリープします。

while (!addNumbersResp.isDone()) {
Thread.sleep(100);

3. レスポンスをポーリングします。

AddNumbersResponse reply = addNumbersResp.get();

レスポンスへのリクエスト・コンテキストの伝播

WebLogic Serverには、リクエストおよびレスポンス・メッセージの内容に関係なく、ビジネス・コンテキスト(ビジネス・レベルのメッセージIDなど)をリクエスト・メッセージにアタッチして、レスポンスが返されたときにアクセスできるようにする強力な機能があります。たとえば、他の方法ではレスポンス・メッセージで利用できないビジネス・レベルのメッセージIDを使用できます。メッセージにこの情報を伝播することにより、レスポンス・メッセージが返されたときに情報にアクセスできます。

Webサービス・クライアントは、シリアライズ可能でさえあれば任意のリクエスト・メッセージ・コンテキスト・プロパティを格納できます。メッセージ・コンテキスト・プロパティは、weblogic.wsee.jaxws.JAXWSProperties.PERSISTENT_CONTEXTマップ・プロパティの一部として格納でき、レスポンス・メッセージが返された後で取得できます。

次の例では、PERSISTENT_CONTEXTマップ・プロパティを使用してメッセージ・コンテキスト・プロパティを定義および設定する方法を示します。

例12-3 メッセージ・コンテキスト・プロパティの設定

import weblogic.wsee.jaxws.JAXWSProperties;
. . .
MyClientPort port = myService.getPort();
Map<String, Serializable> clientPersistProps =
port.getRequestContext().get(JAXWSProperties.PERSISTENT_CONTEXT);
Serializable obj = <my_property>;
clientPersistProps.put("MyProperty", obj);

port.myOperationAsync(<args>, new AsyncHandler<MyOperationResponse>() {
public void handleResponse(Response<MyOperationResponse> res) {
try {
// Get the actual response
MyOperationResponse response = res.get().getReturn();

// Get the property stored when making request. Note, this property did not get
// passed over the wire with the reuqest. The web services runtime stores it.
Map<String, Serializable> clientPersistProps =
res.getContext().get(JAXWSProperties.PERSISTENT_CONTEXT);
Serializable obj = clientPersistProps.get("MyProperty");
// Do something with MyProperty
} catch (Exception e) {
// Error handling
}
}
});
...

Webサービスの非同期呼出しのモニタリング

WebLogic Server管理コンソールを使用して、呼出し、エラー、フォルトの数など、Webサービスを非同期に呼び出すクライアントの実行時情報をモニターできます。Webサービス・クライアントをモニターするには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表で、Webサービス・クライアントがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開し、Webサービス・クライアントが存在するアプリケーション・モジュールをクリックします。「監視」タブ「Webサービス・クライアント」タブの順にクリックします。

接続作成トランスポート・プロトコルを使用している場合、Webサービスまたはクライアントの接続作成匿名エンドポイントを監視できます。非同期エンドポイントごとに、受信メッセージ数、保留メッセージ数など、実行時の監視情報が表示されます。

「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

Webサービスの接続作成匿名エンドポイントを監視するには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表でWebサービスがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開すると、「Webサービス」カテゴリにアプリケーション内のWebサービスのリストが表示されます。Webサービス名をクリックし、「監視」→「ポート」→「接続」を選択します。

Webサービス・クライアントの接続作成匿名エンドポイントを監視するには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表でWebサービス・クライアントがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開し、Webサービス・クライアントが存在するアプリケーション・モジュールをクリックします。「監視」タブ「Webサービス・クライアント」タブの順にクリックします。次に、「監視」→「サーバー」→「接続作成」をクリックします。

非同期Webサービス・メッセージングのクラスタリングの考慮事項

Webサービス・クライアントがクラスタで実行するときは、非同期呼出しの非同期レスポンス・エンドポイントにレスポンス・メッセージを正しく配信できるように、特別に考慮する必要があります。「非同期クライアント・トランスポート機能の有効化と構成」で説明したように、非同期レスポンス・エンドポイントはAsyncClientTransportFeatureで定義します。

次の図で示すようなシナリオについて考えます。

図12-3 エラーになるクラスタリング・シナリオ

前の図で示されているシナリオ:

- 2つのノードから成るクラスタがクライアント・アプリケーションをホストします。ノード名はServer1とServer2です。クラスタには簡単なロード・バランシング・フロントエンド・プロキシが含まれます。

- クライアント・アプリケーションはClientWebAppという名前のWebアプリケーションで、クラスタに同じようにデプロイされています。つまり、Webアプリケーションはクラスタ内の両方のメンバー・サーバーで実行します。

- ClientWebAppアプリケーションの外部クライアントが、クラスタのフロントエンド・アドレスを通してリクエストを行います。

次のようなシーケンスについて考えます。

1. 外部クライアントは、クラスタのフロントエンドを介してClientWebAppにページを要求します。

2. クラスタのフロントエンドはページ・リクエストのロード・バランシングを行い、Server1のClientWebAppにページ・リクエストを送ります。

3. Server1のClientWebAppはWebサービス・クライアントBackendServiceClientのインスタンスを作成し、バックエンド・サービスBackendServiceと通信します。BackendServiceClientを作成すると、BackendServiceClientを使用して非同期リクエストを行うときに常に非同期レスポンスを受信するための非同期レスポンス・エンドポイントが公開されます。

4. Server1のClientWebAppはBackendServiceClient.doSomethingAsync()を呼び出して、バックエンド・サービスで操作を実行します。非同期レスポンス・エンドポイントのアドレスはReplyToアドレスに含まれます。このアドレスはクラスタのフロントエンドのアドレスで開始しており、Server1のアドレスではありません。

5. クラスタがdoSomething操作に対するレスポンスを受信します。

6. クラスタはメッセージをロード・バランシングし、今度はServer2にメッセージを送ります。

7. Server2にはレスポンスを受信するための非同期レスポンス・エンドポイントがないので、メッセージの配信は失敗します。

この問題を解決するには、次のどちらかを使用できます。

- SOAP対応のクラスタ・フロントエンド・プロキシ・プラグイン(WebLogic Server HttpClusterServletなど)を使用します。詳細は、『Oracle WebLogic Serverクラスタの管理』のプロキシ・プラグインの構成に関する項を参照してください。たとえばクラスタのフロントエンド・テクノロジが標準化されているような場合、この解決方法は使用できない場合があります。

- クラスタ内のすべてのメンバー・サーバーが非同期レスポンス・エンドポイントを公開して、非同期レスポンス・メッセージを任意のメンバー・サーバーに配信できるようにし、必要に応じてインプレース・クラスタ・ルーティングを介して正しいサーバーにメッセージを転送します。

第2の方法を実装するには、シングルトン・ポート・インスタンスを定義し、その初期化をクライアント・コンテナの初期化時(デプロイメント時)に行うことをお薦めします。クラスタの非同期レスポンス・エンドポイントの初期化のお薦めする方法の例については、例11-1「非同期Webサービス・クライアントのベスト・プラクティスの例」を参照してください。

注意:
コンテナの種類によっては、異なる方法でエンドポイントを初期化することもできます。たとえば、クライアントがWebサービスでホストされている場合、Webサービス・コンテナのメソッドに@PostConstructアノテーションを付けることができ、そのメソッドでシングルトン・ポートを初期化できます。EJBコンテナでは、シングルトン・ポートを作成するためのトリガー・ポイントとしてejbCreate()メソッドを使用できます。

13 信頼性のあるWebサービスとクライアントを開発するためのロードマップ

この章では、WebLogic Server 12.1.3のJava API for XML Web Services (JAX-WS)用のWebLogic Webサービスおよびクライアントを開発するためのベスト・プラクティスについて説明します。

この章の内容は次のとおりです:

- 信頼性のあるWebサービス・クライアントを開発するためのロードマップ

- 信頼性のあるWebサービスを開発するためのロードマップ

- ファイアウォールの背後から信頼性のあるWebサービスにアクセスする(接続を作成する)ためのロードマップ

- 信頼性のあるWebサービスを保護するためのロードマップ

注意:
「Webサービス永続性を構成する手順」も参照してください。

信頼性のあるWebサービス・クライアントを開発するためのロードマップ

表13-1では、信頼性のあるWebサービス・クライアントを開発するためのベスト・プラクティスとその例を示します。これらのガイドラインは、第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」で示されているガイドラインと併せて使用する必要があります。

表13-1 信頼性のあるWebサービス・クライアントを開発するためのロードマップ

ベスト・プラクティス

説明

常に信頼性エラー・リスナーを実装します。

詳細は、「信頼性エラー・リスナーの実装」を参照してください。

メッセージを作業単位にグループ化します。

送信されるすべてのメッセージでRMシーケンスの作成と終了のプロトコル・オーバーヘッドを発生させるのではなく、メッセージをビジネス作業単位にグループ化できます(バッチ化とも呼ばれます)。詳細は、「ビジネス作業単位へのメッセージのグループ化(バッチ化)」を参照してください。

注意: このベスト・プラクティスは、例13-1では示されていません。

確認応答の間隔を特定のシナリオに適した現実的な値に設定します。

お薦めする設定は、リクエスト間の通常の間隔の2倍です。詳細は、「確認応答の間隔の構成」を参照してください。

注意: このベスト・プラクティスは、例13-1では示されていません。

基本の再送信間隔を特定のシナリオに適した現実的な値に設定します。

お薦めする設定は、確認レスポンスの間隔または通常のレスポンス時間のどちらか大きい方の2倍です。詳細は、「基本の再送信間隔の構成」を参照してください。

注意: このベスト・プラクティスは、例13-1では示されていません。

タイムアウト(非アクティブおよび順序の有効期限)を特定のシナリオに適した現実的な値に設定します。

詳細は、「非アクティブ・タイムアウトの構成」および「順序の有効期限の構成」を参照してください。

注意: このベスト・プラクティスは、例13-1では示されていません。

次の例では、信頼性のあるWebサービス・クライアントを開発するためのベスト・プラクティスを示します。

例13-1 信頼性のあるWebサービス・クライアントのベスト・プラクティスの例

import java.io.*;
import java.util.*;

import javax.servlet.*;
import javax.xml.bind.JAXBContext;
import javax.xml.ws.*;

import weblogic.jws.jaxws.client.ClientIdentityFeature;
import weblogic.jws.jaxws.client.async.AsyncClientHandlerFeature;
import weblogic.jws.jaxws.client.async.AsyncClientTransportFeature;
import weblogic.wsee.reliability2.api.ReliabilityErrorContext;
import weblogic.wsee.reliability2.api.ReliabilityErrorListener;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;

import com.sun.xml.ws.developer.JAXWSProperties;

/**
* Example client for invoking a reliable web service asynchronously.
*/
public class BestPracticeAsyncRmClient
extends GenericServlet {

private BackendReliableServiceService _service;
private BackendReliableService _singletonPort;
private WebServiceFeature[] _features;

private static int _requestCount;
private static String _lastResponse;
private static final String MY_PROPERTY = "MyProperty";

@Override
public void init()
throws ServletException {

_requestCount = 0;
_lastResponse = null;

// Only create the web service object once as it is expensive to create repeatedly.
if (_service == null) {
_service = new BackendReliableServiceService();
}

// Best Practice: Use a stored list of features, per client ID, to create client instances.
// Define all features for the web service port, per client ID, so that they are
// consistent each time the port is called. For example:
// _service.getBackendServicePort(_features);

List<WebServiceFeature> features = new ArrayList<WebServiceFeature>();

// Best Practice: Explicitly define the client ID.
ClientIdentityFeature clientIdFeature =
new ClientIdentityFeature("MyBackendServiceAsyncRmClient");
features.add(clientIdFeature);

// Best Practice: Always implement a reliability error listener.
// Include this feature in your reusable feature list. This enables you to determine
// a reason for failure, for example, RM cannot deliver a request or the RM sequence fails in
// some way (for example, client credentials refused at service).
WsrmClientInitFeature rmFeature = new WsrmClientInitFeature();
features.add(rmFeature);
rmFeature.setErrorListener(new ReliabilityErrorListener() {
public void onReliabilityError(ReliabilityErrorContext context) {

// At a *minimum* do this
System.out.println("RM sequence failure: " +
context.getFaultSummaryMessage());
_lastResponse = context.getFaultSummaryMessage();

// And optionally do this...

// The context parameter conveys whether a request or the entire
// sequence has failed. If a sequence fails, you will get a notification
// for each undelivered request (if any) on the sequence.
if (context.isRequestSpecific()) {
// Single request failure (possibly as part of a larger sequence failure).
// Retrieve the original request.
String operationName = context.getOperationName();
System.out.println("Failed to deliver request for operation '" +
operationName + "'. Fault summary: " +
context.getFaultSummaryMessage());
if ("DoSomething".equals(operationName)) {
try {
String request = context.getRequest(JAXBContext.newInstance(),
String.class);
System.out.println("Failed to deliver request for operation '" +
operationName + "' with content: " +
request);
Map<String, Serializable> requestProps =
context.getUserRequestContextProperties();
if (requestProps != null) {
// Retrieve the request property. Use MyProperty
// to describe the request that failed and print this value
// during the simple 'error recovery' below.
String myProperty = (String)requestProps.get(MY_PROPERTY);
System.out.println("Got MyProperty value propagated from request: "+
myProperty);
System.out.println(myProperty + " failed!");
}
} catch (Exception e) {
e.printStackTrace();
}
}
} else {
// The entire sequence has encountered an error.
System.out.println("Entire sequence failed: " +
context.getFaultSummaryMessage());

}
}
});

// Asynchronous endpoint.
AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(getServletContext());
features.add(asyncFeature);

// Best Practice: Define a port-based asynchronous callback handler,
// AsyncClientHandlerFeature, for asynchronous and dispatch callback handling.
BackendReliableServiceAsyncHandler handler =
new BackendReliableServiceAsyncHandler() {
public void onDoSomethingResponse(Response<DoSomethingResponse> res) {
// ... Handle Response ...
try {
// Show getting the MyProperty value back.
DoSomethingResponse response = res.get();
_lastResponse = response.getReturn();
System.out.println("Got (reliable) async response: " + _lastResponse);
// Retrieve the request property. This property can be used to
// 'remember' the context of the request and subsequently process
// the response.
Map<String, Serializable> requestProps =
(Map<String, Serializable>)
res.getContext().get(JAXWSProperties.PERSISTENT_CONTEXT);
String myProperty = (String)requestProps.get(MY_PROPERTY);
System.out.println("Got MyProperty value propagated from request: "+
myProperty);
} catch (Exception e) {
_lastResponse = e.toString();
e.printStackTrace();
}
}
};
AsyncClientHandlerFeature handlerFeature =
new AsyncClientHandlerFeature(handler);
features.add(handlerFeature);

// Set the features used when creating clients with
// the client ID "MyBackendServiceAsyncRmClient."

_features = features.toArray(new WebServiceFeature[features.size()]);

// Best Practice: Define a singleton port instance and initialize it when
// the client container initializes (upon deployment).
// The singleton port will be available for the life of the servlet.
// Creation of the singleton port triggers the asynchronous response endpoint to be published
// and it will remain published until our container (Web application) is undeployed.
// Note, we will get a call to destroy() before this.
_singletonPort = _service.getBackendReliableServicePort(_features);
}

@Override
public void service(ServletRequest req, ServletResponse res)
throws ServletException, IOException {

// TODO: ... Read the servlet request ...

// For this simple example, echo the _lastResponse captured from
// an asynchronous DoSomethingResponse response message.

if (_lastResponse != null) {
res.getWriter().write(_lastResponse);
_lastResponse = null; // Clear the response so we can get another
return;
}

// Set _lastResponse to NULL in order to make a new invocation against
// BackendService to generate a new response

// Best Practice: Synchronize use of client instances.
// Create another port using the *exact* same features used when creating _singletonPort.
// Note, this port uses the same client ID as the singleton port and it is effectively the
// same as the singleton from the perspective of the web services runtime.
// This port will use the asynchronous response endpoint for the client ID,
// as it is defined in the _features list.
// NOTE: This is *DEFINITELY* not best practice or ideal because our application is
//       incurring the cost of an RM handshake and sequence termination
//       for *every* reliable request sent. It would be better to send
//       multiple requests on each sequence. If there is not a natural grouping
//       for messages (a business 'unit of work'), then you could batch
//       requests onto a sequence for efficiency. For more information, see
//        Grouping Messages into Business Units of Work (Batching).
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);

// Set the endpoint address for BackendService.
((BindingProvider)anotherPort).getRequestContext().
put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://localhost:7001/BestPracticeReliableService/BackendReliableService");

// Make the invocation. Our asynchronous handler implementation (set
// into the AsyncClientHandlerFeature above) receives the response.
String request = "Protect and serve";
System.out.println("Invoking DoSomething reliably/async with request: " +
request);
// Add a persistent context property that will be returned on the response.
// This property can be used to 'remember' the context of this
// request and subsequently process the response. This property will *not*
// get passed over wire, so the properties can change independent of the
// application message.
Map<String, Serializable> persistentContext =
(Map<String, Serializable>)((BindingProvider)anotherPort).
getRequestContext().get(JAXWSProperties.PERSISTENT_CONTEXT);
String myProperty = "Request " + (++_requestCount);
persistentContext.put(MY_PROPERTY, myProperty);
System.out.println("Request being made (reliably) with MyProperty value: " +
myProperty);
anotherPort.doSomethingAsync(request);

// Return a canned string indicating the response was not received
// synchronously. Client needs to invoke the servlet again to get
// the response.
res.getWriter().write("Waiting for response...");

// Best Practice: Explicitly close client instances when processing is complete.
// If not closed, the port will be closed automatically when it goes out of scope.
// This will force the termination of the RM sequence we created when sending the first
// doSomething request. For a better way to handle this, see
//  Grouping Messages into Business Units of Work (Batching).
// NOTE: Even though the port is closed explicitly (or even if it goes out of scope)
//       the reliable request sent above will still be delivered
//       under the scope of the client ID used. So, even if the service endpoint
//       is down, RM retries the request and delivers it when the service endpoint
//       available. The asynchronous resopnse will be delivered as if the port instance was
//       still available.
((java.io.Closeable)anotherPort).close();
}

@Override
public void destroy() {

try {
// Best Practice: Explicitly close client instances when processing is complete.
// Close the singleton port created during initialization. Note, the asynchronous
// response endpoint generated by creating _singletonPort *remains*
// published until our container (Web application) is undeployed.
((java.io.Closeable)_singletonPort).close();
// Upon return, the Web application is undeployed, and our asynchronous
// response endpoint is stopped (unpublished). At this point,
// the client ID used for _singletonPort will be unregistered and will no longer be
// visible from the Administration Console and WLST.
} catch (Exception e) {
e.printStackTrace();
}
}
}

信頼性のあるWebサービスを開発するためのロードマップ

表13-2では、信頼性のあるWebサービスを開発するためのベスト・プラクティスを示します。ファイアウォールの内側から信頼性のあるWebサービスにアクセスするときのベスト・プラクティスについては、「ファイアウォールの背後から信頼性のあるWebサービスにアクセスする(接続を作成する)ためのロードマップ」を参照してください。

表13-2 信頼性のあるWebサービスを開発するためのロードマップ

ベスト・プラクティス

説明

基本の再送信間隔を特定のシナリオに適した現実的な値に設定します。

詳細は、「基本の再送信間隔の構成」を参照してください。

確認応答の間隔を特定のシナリオに適した現実的な値に設定します。

お薦めする設定は、リクエスト間の通常の間隔の2倍です。詳細は、「確認応答の間隔の構成」を参照してください。

タイムアウト(非アクティブおよび順序の有効期限)を特定のシナリオに適した現実的な値に設定します。

次の点を考慮してください。

- 非常に短期間の交換の場合、デフォルトのタイムアウトでは長すぎて、シーケンスの状態が必要以上に長く維持される場合があります。

- 特定のビジネス作業単位の予想される継続時間の2倍にタイムアウトを設定します。これにより、シーケンスは十分に長く存在できます。

詳細は、「非アクティブ・タイムアウトの構成」および「順序の有効期限の構成」を参照してください。

必要な最低の配信保証(またはサービス品質)を反映した信頼性のあるメッセージング・ポリシーを使用します。

デフォルトでは、配信保証はExactly Once, In Orderに設定されています。順序が必要ない場合、配信保証を単にExactly Onceに設定することで、パフォーマンスを向上させることができます。同様に、重複するリクエストをサービスが許容できる場合は、配信保証をAt Least Onceに設定できます。

信頼性のあるメッセージングの配信保証の詳細は、表14-1「信頼性のあるメッセージングの配信保証」および「Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成」を参照してください。

ファイアウォールの背後から信頼性のあるWebサービスにアクセスする(接続を作成する)ためのロードマップ

表13-3では、接続作成を使用してファイアウォールの内側から信頼性のあるWebサービスにアクセスするためのベスト・プラクティスを示します。これらのガイドラインは、「信頼性のあるWebサービスを開発するためのロードマップ」および第11章「非同期Webサービス・クライアントを開発するためのロードマップ」で示されている一般的なガイドラインと組み合せて使用する必要があります。

ファイアウォールの背後から信頼性のあるWebサービスにアクセスする(接続を作成する)ためのロードマップ

ベスト・プラクティス

説明

信頼性のあるメッセージングの基本の再送信間隔で接続作成のポーリング間隔を調整します。

接続作成トランスポートに対して設定するポーリング間隔は、信頼性のあるメッセージング・プロトコルのメッセージがクライアントとサービスの間を往復するのに要する時間の下限を設定します。信頼性のあるメッセージングの基本の再送信間隔を接続作成ポーリング間隔に近い値に設定した場合、信頼性のあるメッセージングのリクエストがWebサービスによって受信され、信頼性のあるメッセージングのランタイムがリクエストの再送信を試みる前に関連するRM確認応答がリクエストに対して送信される(最善で1接続作成ポーリング間隔後に)可能性が低くなります。信頼性のあるメッセージングの基本の再送信間隔を低すぎる値に設定すると、リクエストに対して不必要な再送信が発生し、重複する着信リクエストの処理が試みられて、接続作成がリクエストからレスポンスを取得するためにメッセージをポーリングするため、サービス側で負荷が連鎖的に発生する可能性があります。

基本の再送信間隔は接続作成ポーリング間隔の2倍以上の値に設定することをお薦めします。

注意: Webサービスの信頼性のあるメッセージングと接続作成を併用すると、接続作成のポーリング間隔が必要に応じて実行時に調整され、信頼性のあるメッセージングの基本の再送信間隔より少なくとも3秒小さい値に設定されます。基本の再送信間隔が3秒以下の場合は、接続作成のポーリング間隔は基本の再送信間隔の値に設定されます。

接続作成のポーリング間隔と信頼性のあるメッセージングの基本の再送信間隔の設定の詳細は、それぞれ、「ポーリング間隔の構成」および「基本の再送信間隔の構成」を参照してください。

信頼性のあるWebサービスを保護するためのロードマップ

表13-4では、WS-SecureConversationを使用して信頼性のあるWebサービスを保護するためのベスト・プラクティスを示します。これらのガイドラインは、「信頼性のあるWebサービスを開発するためのロードマップ」で示されているガイドラインと併せて使用する必要があります。

表13-4 信頼性のあるWebサービスを保護するためのロードマップ

ベスト・プラクティス

説明

信頼性のあるメッセージングの基本の再送信間隔および確認応答の間隔でWS-SecureConversationの存続期間を調整します。

信頼性のあるメッセージングの基本の再送信間隔および確認応答の間隔に近い値、またはそれより小さい値に、WS-SecureConversationの存続期間を設定すると、信頼性のあるメッセージングのハンドシェイク・メッセージをWebサービスに送信できる前に、WS-SecureConversationトークンの有効期限が切れる可能性があります。このため、WS-SecureConversationの存続期間は、基本の再送信間隔の2倍以上に設定することをお薦めします。

基本の再送信間隔の設定の詳細は、「基本の再送信間隔の構成」を参照してください。

14 Webサービスの信頼性のあるメッセージングの使用

この章では、Java API for XML Web Services (JAX-WS)を使用するWebLogic Server 12.1.3用のWebLogic Webサービスで、Webサービスの信頼性のあるメッセージング(WS-ReliableMessaging)を使用する方法について説明します。

「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」も参照してください。

この章の内容は次のとおりです:

- Webサービスの信頼性のあるメッセージングの概要

- 信頼性のあるWebサービスの作成および呼出し手順

- 送信元と宛先のWebLogic Serverインスタンスの構成

- Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成

- 信頼性のあるJWSファイルに関するプログラミングのガイドライン

- Webサービス・クライアントからの信頼性のあるWebサービスの呼出し

- 信頼性のあるメッセージングの構成

- 信頼性エラー・リスナーの実装

- 信頼性のあるメッセージ・シーケンスのライフサイクルの管理

- Webサービスの信頼性のあるメッセージングの監視

- ビジネス作業単位へのメッセージのグループ化(バッチ化)

- 信頼性のあるWebサービスを再デプロイする際にクライアント側で考慮すべき事項

- WebLogic Web サービスの信頼性のあるメッセージングとの相互運用性

WebLogic Serverのサンプル・サーバーには、信頼性のあるメッセージングに関する次の3つのサンプルが含まれています。

- JAX-WS Webサービスでの信頼性のあるメッセージングの構成

- JAX-WS Webサービスでの接続作成および信頼性のあるメッセージングの使用

- JAX-WS Webサービスでの保護された信頼性のあるメッセージングの構成

詳細は、『Oracle WebLogic Server WebLogic Webサービスの理解』のWebLogic Sererディストリビューション内のWebサービスの例に関する項を参照してください。

Webサービスの信頼性のあるメッセージングの概要

Webサービスの信頼性のあるメッセージングとは、ある1つのアプリケーション・サーバーで実行中のアプリケーションが、別のアプリケーション・サーバーで実行中のWebサービスを確実に呼び出せるフレームワークです。ここでは、双方のサーバーでWS-ReliableMessaging仕様が実装されていることが前提となっています。信頼性が高いとは、ソフトウェア・コンポーネント、システム、またはネットワークの障害があっても、2つのエンドポイント(Webサービスとクライアント)間でメッセージ配信を保証することができる状態として定義されます。

WebLogic Webサービスは、WS-ReliableMessaging 1.2仕様(2009年2月)(http://docs.oasis-open.org/ws-rx/wsrm/200702)に準拠しています(また、バージョン1.1をサポートしています)。この仕様では、異なるアプリケーション・サーバー上の2つのエンドポイント(Webサービスとクライアント)が確実に通信できる方法について記述されています。具体的には、この仕様では送信元エンドポイント(つまりクライアントWebサービス)から宛先エンドポイント(つまり操作を確実に呼び出せるWebサービス)へ送信されるメッセージが、1つ以上の配信保証に基づいて確実に配信されるか、そうでなければ必ずエラーが発生する、相互運用性を備えたプロトコルについて説明されています。

信頼性のあるWebLogic Webサービスには、次の配信保証が備わっています。

表14-1 信頼性のあるメッセージングの配信保証

配信保証

説明

At Most Once

メッセージは最大で1回、重複なしに配信されます。メッセージによっては、一度も配信されない可能性もあります。

At Least Once

すべてのメッセージが、少なくとも1回、配信されます。メッセージによっては、1回よりも多く配信される可能性があります。

Exactly Once

すべてのメッセージが、必ず1回重複なしに配信されます。

In Order

メッセージは、送信された順序で配信されます。この配信保証は、上記の3つの保証と組み合せることも可能です。

次の項では、信頼性のあるWebサービスとクライアントの作成方法、およびWebサービスをデプロイするWebLogic Serverインスタンスの構成方法について説明します。

WS-Policyを使用した信頼性のあるメッセージング・ポリシーのアサーションの指定

WebLogic Webサービスでは、宛先エンドポイントがWebサービスの信頼性のあるメッセージングの機能と要件を記述および公開できるように、WS-Policyファイルを使用します。WS-Policyファイルは、サポートされているWS-ReliableMessaging仕様のバージョンやサービス品質の要件などが記述されたXMLファイルです。WS-Policy仕様(http://www.w3.org/TR/ws-policy/)では、Webサービスのポリシーを記述して通信するための、汎用的なモデルと構文が提供されています。

WebLogic Serverには、標準的な信頼性のあるメッセージング・アサーションを含むあらかじめパッケージ化されているWS-Policyファイルがあります。「Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」を参照してください。あらかじめパッケージ化されているWS-Policyファイルがニーズに合わない場合は、独自のWS-Policyファイルを作成する必要があります。詳細は、「Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成」を参照してください。信頼性のあるメッセージングのポリシー・アサーションに関するリファレンス情報は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスの信頼性のあるメッセージングのポリシー・アサーションに関するリファレンスの項を参照してください。

信頼性のあるメッセージングでサポートされるトランスポート・タイプ

Webサービスの信頼性のあるメッセージングは、非同期的または同期的に使用できます。メッセージを非同期に配信するときは、必要に応じて、メッセージ配信の自動再試行をサポートするようにバッファリングを構成できます。

次の表では、Webサービスの信頼性のあるメッセージングに対するトランスポート・タイプのサポートを示します。Webサービス・クライアントのトランスポート・タイプのサポートの詳細は、「Webサービス・クライアントからの信頼性のあるWebサービスの呼出し」を参照してください。障害リカバリの詳細は、「信頼性のあるメッセージングの障害リカバリのシナリオ」を参照してください。

注意:
メッセージ・バッファリングは、Webサービスに対して構成できます。詳細は、第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。Webサービス・クライアントの場合、メッセージ・バッファリングはデフォルトで有効化されています。

表14-2 Webサービスの信頼性のあるメッセージングのトランスポート・タイプ

トランスポート・タイプ

特徴

非同期トランスポート

バッファ付きWebサービスの場合:

- 最も堅牢な使用モードですが、最も多くのオーバーヘッドを必要とします。

- メッセージ配信を自動的に再試行します。

- ネットワークが停止しても維持されます。

- 送信元エンドポイントまたは宛先エンドポイントを再起動できます。

- 非匿名ReplyToを使用します。

- 非同期クライアント・トランスポートを使用すると、1つのスレッドで複数のリクエストを処理でき、負荷をいっそう効率よく緩和できます。詳細は、「スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)」を参照してください。

- Webサービス・クライアントは、非同期または同期の呼出しセマンティクスを使用して、Webサービスを呼び出すことができます。詳細は、表12-1「非同期Webサービス呼出しのサポート」を参照してください。

非バッファWebサービスの場合:

- 非同期のバッファ付き使用モードよりオーバーヘッドが少なくなります。

- 順序の状態のみが保持されます。

- 非匿名ReplyToを使用します。

- Webサービス・クライアントは、非同期または同期の呼出しセマンティクスを使用して、Webサービスを呼び出すことができます。詳細は、表12-1「非同期Webサービス呼出しのサポート」を参照してください。

同期トランスポート

- オーバーヘッドは最も少なく、最も簡単なプログラミング・モデルです。

- 匿名ReplyToを使用します。

- Webサービス・クライアントは、非同期または同期の呼出しセマンティクスを使用して、Webサービスを呼び出すことができます。詳細は、表12-1「非同期Webサービス呼出しのサポート」を参照してください。

- Webサービス・クライアントが同期トランスポートを使用してバッファ付きWebサービスを呼び出した場合、結果は次のいずれかになります。
- シーケンスの最初のリクエストの場合、宛先のシーケンスはバッファなしに設定されます(Webサービスの構成がバッファなしとして設定されていた場合と同様)

- シーケンスの最初のリクエストではない場合は(つまり、クライアントが前に非同期トランスポートを使用してリクエストを送信していた場合)、リクエストは破棄されてエラーが返されます。

信頼性のあるメッセージ・シーケンスのライフサイクル

次の図に、信頼性のあるメッセージの一方向の交換を示します。

図14-1 Webサービスの信頼性のあるメッセージの交換

信頼性のあるメッセージ・シーケンスは、RM送信元とRM宛先の間で確実に交換されるメッセージ・セットの進捗状況を追跡する際に使用されます。シーケンスは、0個以上のメッセージの送信に使用でき、文字列識別子で識別されます。この識別子は、信頼性のあるメッセージングを使用する際に、そのシーケンスを参照するために使用されます。

Webサービス・クライアント・アプリケーションは、RM送信元がRM宛先へ送信する信頼性のある配信のメッセージを送信します。RM宛先は、信頼性のあるメッセージを受信したことを確認応答し、そのメッセージをWebサービス・アプリケーションに配信します。RM送信元は、確認応答を受け取るまでメッセージを再送信できます。RM宛先は、リクエストをバッファリングするように構成されている場合は、Webサービスがリクエストの処理に失敗すると、Webサービスにリクエストを再配信できます。

Webサービス・クライアントは、クライアント・インスタンス(ポート・インスタンスまたはディスパッチ・インスタンス)でメソッドを呼び出して、ターゲットWebサービスにメッセージを送信します。ポートは、ポート・タイプの信頼性のあるWebサービスと関連付けられていて、そのサービスに対するプログラム・インタフェースを表します。ポートは、jwsc Antタスクの<clientgen子要素で作成されます。ディスパッチ・インスタンスはクライアントからWebサービスにメッセージ全体を配信するための、緩やかに型指定された汎用インタフェースです。ディスパッチ・クライアントの詳細は、「Webサービス・ディスパッチ・クライアントの開発」を参照してください。

WebLogicでは、このクライアント・インスタンス内に、信頼性のあるメッセージ・シーケンスの識別子が格納されます。これによって、信頼性のあるメッセージ・シーケンスが単一のクライアント・インスタンスに接続されます。特定のクライアント・インスタンスを使用して送信されるすべてのメッセージは、その送信メッセージ数に関係なく、同じ信頼性のあるメッセージ・シーケンスを使用します。(バッチ化を使用しない場合は、「ビジネス作業単位へのメッセージのグループ化(バッチ化)」を参照してください。)

WebLogic Serverには、信頼性のあるシーケンスに関連付けられたリソースが保持されるため、タイミングよくリソースを解放する手順を踏むことをお薦めします。この手順は、クライアント・インスタンス自体のライフサイクルを管理するか、またはweblogic.wsee.reliability2.api.WsrmClient APIを使用して実行できます。WsrmClient APIを使用すると、構成オプションの設定、シーケンスIDの取得、信頼性のあるシーケンスの終了といった一般的なタスクを実行できます。詳細は、「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」を参照してください。

信頼性のあるメッセージングの障害リカバリのシナリオ

次の項では、さまざまなシナリオでの信頼性のあるメッセージングの障害リカバリの概要について説明します。

- リクエストが到着する前にRM宛先がダウンする

- リクエストが行われた後でRM送信元がダウンする

- リクエストが到着した後でRM宛先がダウンする

- バッファなしの信頼性のあるWebサービスでの障害シナリオ

最初の3つのシナリオでは、Webサービスとクライアントの両方でバッファリングが有効であるものとします。最後のシナリオでは、バッファなしのWebサービスでの信頼性のあるメッセージングの障害リカバリについて説明します。バッファリングは、Webサービス・クライアントではデフォルトで有効になります。Webサービスでのバッファリングの構成の詳細は、第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。

リクエストが到着する前にRM宛先がダウンする

表14-3では、RM送信元からのリクエストが到着する前にRM宛先が使用できなくなったときの、信頼性のあるメッセージングの障害リカバリ・シナリオについて説明します。

Webサービスとクライアントの両方でWebサービス・バッファリングが有効であるものとします。バッファリングは、Webサービス・クライアントではデフォルトで有効になります。Webサービスでのバッファリングの構成の詳細は、第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。

表14-3 信頼性のあるメッセージングの障害リカバリのシナリオ: リクエストが到着する前にRM宛先がダウンする

トランスポート・タイプ

シナリオの説明

非同期トランスポート

1. クライアントが非同期メソッドを呼び出します。

2. 信頼性のあるメッセージングのランタイムがリクエストを受け付けます。クライアントは他の作業に戻ります。

3. 信頼性のあるメッセージングのランタイムはリクエストの配信を試みますが、RM宛先がダウンしているため失敗します。

4. 信頼性のあるメッセージングのランタイムは再試行間隔だけ待ってから、リクエストの送信を再び試みます。リクエストの配信は再び失敗します。

5. RM宛先が起動します。

6. 信頼性のあるメッセージングのランタイムは再試行間隔だけ待ってから、リクエストの送信を再び試みます。リクエストの配信が成功します。

7. リクエストのメッセージ番号を含む確認応答が、クライアントに送信されます。信頼性のあるメッセージングのランタイムは再試行リストからメッセージを削除します。

8. レスポンスが到着し、クライアントはそれを処理します。

注意: 「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」で説明されているように、クライアントはいつでも、確認応答のステータスを確認したり、メッセージについての情報にアクセスしたりできます。

同期トランスポート

1. クライアントが同期メソッドを呼び出します。

2. 信頼性のあるメッセージングのランタイムはリクエストを受け付け、クライアントのスレッドをブロックします。

3. 信頼性のあるメッセージングのランタイムはリクエストの配信を試みますが、RM宛先がダウンしているため失敗します。

4. 信頼性のあるメッセージングのランタイムは再試行間隔だけ待ってから、リクエストの送信を再び試みます。リクエストの配信は再び失敗します。

5. RM宛先が起動します。

6. 信頼性のあるメッセージングのランタイムは再試行間隔だけ待ってから、リクエストの送信を再び試みます。リクエストの配信が成功します。

7. レスポンスと確認応答は、トランスポート戻りチャネルを通してクライアントに送信されます。確認応答には、リクエストのメッセージ番号が含まれます。信頼性のあるメッセージングのランタイムは再試行リストからメッセージを削除します。

8. 信頼性のあるメッセージングのランタイムはクライアント・スレッドのブロックを解除し、レスポンスを返します。

9. クライアントは、メソッド呼出しの戻り値としてレスポンスを受け取り、レスポンスを処理します。

注意: 「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」で説明されているように、クライアントはいつでも、確認応答のステータスを確認したり、メッセージについての情報にアクセスしたりできます。

注意: 同期トランスポートで真の信頼性を実現するには、接続作成を使用することをお薦めします。詳細は、「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照してください。

リクエストが行われた後でRM送信元がダウンする

表14-4では、リクエストを行った後でRM送信元がダウンするときの、信頼性のあるメッセージングの障害リカバリ・シナリオについて説明します。

Webサービスとクライアントの両方でWebサービス・バッファリングが有効であるものとします。バッファリングは、Webサービス・クライアントではデフォルトで有効になります。Webサービスでのバッファリングの構成の詳細は、第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。

表14-4 信頼性のあるメッセージングの障害リカバリのシナリオ: リクエストを行った後でRM送信元がダウンする

トランスポート・タイプ

シナリオの説明

非同期トランスポート

1. クライアントが非同期メソッドを呼び出します。

2. 信頼性のあるメッセージングのランタイムがリクエストを受け付けます。クライアントは他の作業に戻ります。

3. クライアント(RM送信元)がダウンします。

4. クライアントが起動します。クライアントは、同じクライアントIDを使用してクライアント・インスタンスを初期化する必要があります。ランタイムは、このクライアントIDを使用して、クライアントに対してアクティブであった信頼性のあるシーケンスIDを取得します。詳細は、「クライアントIDの管理」を参照してください。

5. 信頼性のあるメッセージングのランタイムは、クライアントがダウンする前に使用中であった信頼性のあるシーケンスIDを検出し、受け付けたリクエストを回復します。
注意: リクエストの配信はクライアント・インスタンスによって提供されたリソースに依存するので、この手順は、リクエストの送信に使用されたクライアント・インスタンスをクライアントが再初期化した後でのみ実行されます。クライアントでは、静的ブロック内でクライアント・インスタンスを初期化するか、@PostConstructアノテーションを使用するか、クライアント・インスタンスの早い初期化が保証される他のメカニズムを使用することをお薦めします。詳細は、第11章「非同期Webサービス・クライアントを開発するためのロードマップ」で示されているベスト・プラクティスの例を参照してください。

6. 信頼性のあるメッセージングのランタイムがリクエストを送信し、成功します。

7. リクエストのメッセージ番号を含む確認応答が、クライアントに送信されます。信頼性のあるメッセージングのランタイムは再試行リストからメッセージを削除します。

8. レスポンスが到着し、クライアントはそれを処理します。

注意: 「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」で説明されているように、クライアントはいつでも、確認応答のステータスを確認したり、メッセージについての情報にアクセスしたりできます。

同期トランスポート

1. クライアントが同期メソッドを呼び出します。

2. 信頼性のあるメッセージングのランタイムはリクエストを受け付け、クライアントのスレッドをブロックします。

3. 信頼性のあるメッセージングのランタイムがリクエストの配信を試みます。リクエストの配信が成功します。

4. レスポンスを送信できる前に、クライアント(RM送信元)がダウンします。VMが終了するので、クライアント・スレッドが、呼出し状態およびクライアント自体の呼出しスタックと共に失われます。

5. クライアント(RM送信元)が起動します。クライアントは、同じクライアントIDを使用してクライアント・インスタンス(ポートまたはディスパッチ)を再初期化します。詳細は、「クライアントIDの管理」を参照してください。

6. 信頼性のあるメッセージングのランタイムは、クライアントの以前のシーケンスIDを検出し、最後のリクエストが同期的に行われたことを確認します。

7. 信頼性のあるメッセージングのランタイムは、そのリクエストに対して永久的障害通知を配信し、クライアント・インスタンスと関連付けられているRMシーケンス全体を失敗させます。クライアント・インスタンスと関連付けられているすべてのReliabilityErrorListenerが、この時点で呼び出されます。

8. クライアントは、元のリクエストを取得し(何らかのクライアント固有のメカニズムを使用して)、リクエストでクライアント・インスタンスを再度呼び出してリクエストを再送信します。

注意: 「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」で説明されているように、クライアントはいつでも、確認応答のステータスを確認したり、メッセージについての情報にアクセスしたりできます。

注意: 同期トランスポートで真の信頼性を実現するには、接続作成を使用することをお薦めします。詳細は、「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照してください。

リクエストが到着した後でRM宛先がダウンする

表14-5では、RM送信元からのリクエストを受け付けた後でRM宛先が使用できなくなったときの、信頼性のあるメッセージングの障害リカバリ・シナリオについて説明します。

Webサービスとクライアントの両方でWebサービス・バッファリングが有効であるものとします。バッファリングは、Webサービス・クライアントではデフォルトで有効になります。Webサービスでのバッファリングの構成の詳細は、第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。

表14-5 信頼性のあるメッセージングの障害リカバリのシナリオ: リクエストが到着した後でRM宛先がダウンする

トランスポート・タイプ

シナリオの説明

非同期トランスポート

1. クライアントが非同期メソッドを呼び出します。

2. 信頼性のあるメッセージングのランタイムがリクエストを受け付けます。クライアントは他の作業に戻ります。

3. 信頼性のあるメッセージングのランタイムがリクエストの配信を試み、成功します。

4. RM宛先はリクエストを受け付けて、戻りチャネルで確認応答を送信します。

5. 信頼性のあるメッセージングのランタイムは確認応答を受け取り、再試行リストからメッセージを削除します。

6. RM宛先がダウンします。

7. RM送信元の信頼性のあるメッセージングのランタイムは、この間に保留中のリクエストを再試行します。

8. RM宛先が起動します。

9. RM宛先は格納されているリクエストを回復し、処理して、レスポンスを送信します。

10. レスポンスが到着し、クライアントはそれを処理します。

注意: 「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」で説明されているように、クライアントはいつでも、確認応答のステータスを確認したり、メッセージについての情報にアクセスしたりできます。

同期トランスポート

注意: 同期トランスポートを使用してバッファ付きWebサービスを呼び出そうとした場合、結果は次のいずれかになります。

- シーケンスの最初のリクエストの場合、宛先のシーケンスはバッファなしに設定されます(Webサービスの構成がバッファなしとして設定されていた場合と同様)。

- シーケンスの最初のリクエストではない場合は(つまり、クライアントが前に非同期トランスポートを使用してリクエストを送信していた場合)、リクエストは破棄されてエラーが返されます。

次にこのシナリオのシーケンスを説明します。

1. クライアントが同期メソッドを呼び出します。

2. 信頼性のあるメッセージングのランタイムはリクエストを受け付け、クライアントのスレッドをブロックします。

3. 信頼性のあるメッセージングのランタイムがリクエストの配信を試みます。リクエストの配信が成功します。

4. RM宛先はリクエストを受け付けて、トランスポート戻りチャネルで確認応答を送信します。

5. クライアント(RM送信元)は確認応答を検出し、再試行リストからリクエストを削除します。

6. RM宛先がダウンします。

7. クライアント・スレッドはブロックされたままになります。

8. RM宛先が起動して回復し、リクエストを処理して、クライアントにレスポンスを送信します。

9. 信頼性のあるメッセージングのランタイムはクライアント・スレッドのブロックを解除し、レスポンスを返します。

10. クライアントは、メソッド呼出しの戻り値としてレスポンスを受け取り、レスポンスを処理します。

注意: 「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」で説明されているように、クライアントはいつでも、確認応答のステータスを確認したり、メッセージについての情報にアクセスしたりできます。

バッファなしの信頼性のあるWebサービスでの障害シナリオ

バッファなしWebサービスの動作はバッファ付きWebサービスとは異なり、リクエストの確認応答と処理を行う前に、強化されたストレージに要求をバッファリングしません。バッファなしWebサービスはサービス・ロジックが失敗した場合でもリクエストを再処理しませんが、バッファ付きWebサービスはリクエストを再処理します。どちらの場合も、Webサービスによって生成されるすべてのレスポンスは、クライアントに返送される前にバッファリングされます。

バッファなしWebサービスは、次の場合に有効である場合があります。

- Webサービスが非トランザクション・リソースに対して動作しており、リクエストを2回以上処理する必要がない場合(バッファリングされたリクエストをデキューしたトランザクションのロールバックでは、非トランザクション・サービスの二次的影響をロールバックできないため)。

- Webサービスが比較的軽量であり、リクエストの処理に時間がかからない場合。

- Webサービスではパフォーマンスが最も重要であり、リクエストまたはレスポンスを失ってもかまわない場合。バッファなしWebサービスではリクエストをストアにバッファリングするオーバーヘッドがないため、バッファ付きWebサービスよりスループットがよくなります。パフォーマンスの向上は、リクエストをバッファリングするために必要な時間とリソースによって異なります(たとえば、非常に大きいリクエスト・メッセージでは、バッファリングに多くの時間とリソースが必要な場合があります)。

ほとんどの障害シナリオでは、バッファなしWebサービスの動作はバッファ付きWebサービスとほぼ同じです。例外は、サービス(RM宛先)自体で障害が発生した場合です。たとえば、説明したすべてのRM送信元障害シナリオでは、動作はバッファ付きWebサービスでもバッファなしWebサービス(RM宛先)でも同じです。バッファなしWebサービスでは、次の2つのポイントの間で障害ウィンドウが開きます。

- リクエストが処理のために受け付けられます。

- Webサービスからのレスポンスがクライアント(RMリソース)への配信のために登録されます。

これら2つのポイントの間でWebサービス(RM宛先)に障害が起きると、RM送信元はリクエストが正常に処理されたものと判断しますが(確認応答を受け取ったため)、レスポンスを受け取ることはなく、リクエストが処理されない可能性があります。

Webサービスをバッファなしとして実行するように構成する前に、この障害ウィンドウをよく検討してください。

信頼性のあるWebサービスの作成および呼出し手順

WebLogic Webサービスの信頼性のあるメッセージングを構成するには、JMSサーバーやストア・アンド・フォワード(SAF)・エージェントの作成など標準的なJMSタスクとともに、JWSファイルへのJWSアノテーションの追加などWebサービス固有のタスクを実行する必要があります。また、あらかじめパッケージ化されているファイルを使用しない場合は、必要に応じて、信頼性のあるWebサービスの信頼性のあるメッセージング機能を記述したカスタムWS-Policyファイルをユーザー側で作成します。

信頼性のあるWebサービスの呼出しにWebLogicクライアントAPIを使用している場合、クライアント・アプリケーションはWebLogic Server上で実行される必要があります。したがって構成タスクを、Webサービス・クライアントのコードがデプロイされる送信元WebLogic Serverインスタンスと、信頼性のあるWebサービスそのものがデプロイされる宛先WebLogic Serverインスタンスの双方で実行する必要があります。

表14-6は、信頼性のあるWebサービスと、その操作を呼び出すクライアントを作成する手順を説明しています。この手順では、Webサービスとクライアントを実装するJWSファイルをゼロから作成する方法を示しています。既存のJWSファイルを更新する場合は、この手順をガイドとして利用してください。またこの手順では、ソースWebLogic Serverインスタンスと宛先WebLogic Serverインスタンスの構成方法も示しています。

以下の作業を完了している必要があります。

- 宛先と送信元のWebLogic Serverインスタンスを作成しておきます。信頼性のあるWebサービスを宛先WebLogic Serverインスタンスにデプロイし、信頼性のあるWebサービスを呼び出すクライアントを送信元WebLogic Serverインスタンスにデプロイします。

- Antベースの開発環境を設定しておきます。

- 編集(jwsc Antタスクを実行して信頼性のある生成済Webサービスをデプロイするためのターゲットの追加など)が可能な作業用のbuild.xmlファイルの用意。

詳細は、第3章「JAX-WS Webサービスの開発」を参照してください。非同期および信頼性のあるWebサービスとクライアントの開発のベスト・プラクティスは、「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

表14-6 信頼性のあるWebサービスの作成および呼出しの手順

#

手順

説明

1

宛先WebLogic ServerインスタンスとソースWebLogic Serverインスタンスを構成します。

信頼性のあるWebサービスを宛先WebLogic Serverインスタンスにデプロイし、信頼性のあるWebサービスを呼び出すクライアントを送信元WebLogic Serverインスタンスにデプロイします。宛先WebLogic Serverインスタンスの構成の詳細は、「送信元と宛先のWebLogic Serverインスタンスの構成」を参照してください。

2

WS-Policyファイルを作成する(オプション)

任意のXMLまたはプレーン・テキスト・エディタを使用し、必要に応じて宛先WebLogic Server上で実行されているWebサービスの信頼性のあるメッセージング機能が記述されたWS-Policyファイルを作成します。独自のWS-Policyファイルを作成する方法の詳細は、「Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成」を参照してください。

注意: WebLogic Serverに付属しているいずれかのWS-Policyファイルを使用する場合、この手順は不要です。詳細は、付録A「Web Services Reliable Messagingと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」を参照を参照してください。

3

信頼性のあるWebサービスを実装するJWSファイルを作成および更新します。

このWebサービスは、宛先WebLogic Serverインスタンスにデプロイされます。「信頼性のあるJWSファイルに関するプログラミングのガイドライン」を参照してください。

たとえばベスト・プラクティスについては、「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

4

信頼性のあるWebサービスのコンパイルに使用されるbuild.xmlファイルを更新します。

build.xmlファイルを更新して、信頼性のあるJWSファイルをWebサービスにコンパイルするjwsc Antタスクの呼出しを含めます。

jwscタスクの使用に関する一般的な情報は、「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

5

信頼性のあるJWSファイルをコンパイルおよびデプロイします。

適切なターゲットを呼び出して信頼性のあるJWSファイルをコンパイルし、宛先WebLogic Serverにデプロイします。例:

prompt> ant build-reliableService deploy-reliableService

6

Webサービス・クライアントを作成または更新します。

Webサービス・クライアントは、信頼性のあるWebサービスを呼び出し、送信元WebLogic Serverにデプロイされます。「Webサービス・クライアントからの信頼性のあるWebサービスの呼出し」を参照してください。

7

信頼性のあるメッセージングを構成します。(オプション)

WebLogic Server管理コンソールを使用して信頼性のあるWebサービスに対する信頼性のあるメッセージングを構成します。信頼性のあるWebサービスにアタッチされているWS-Policyファイルが、初期構成の設定を提供します。「信頼性のあるメッセージングの構成」を参照してください。

8

信頼性エラー・リスナーを実装します。(オプション)

信頼性のある配信が失敗した場合に通知を受け取る信頼性エラー・リスナーを実装します。「信頼性エラー・リスナーの実装」を参照してください。

9

信頼性のあるメッセージ・シーケンスのライフサイクルを管理します。(オプション)

WebLogic Serverでは、Webサービスの信頼性のあるメッセージングで使用するためのクライアントAPI weblogic.wsee.reliability2.api.WsrmClientが提供されています。このAPIを使用して、構成オプションの設定、信頼性のあるシーケンスIDの取得、信頼性のあるシーケンスの終了などの一般的なライフサイクル・タスクを実行します。詳細は、「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」を参照してください。

10

クライアントWebサービスのコンパイルに使用されるbuild.xmlファイルを更新します。

build.xmlファイルを更新して、信頼性のあるJWSファイルをWebサービスにコンパイルするjwsc Antタスクの呼出しを含めます。

jwscタスクの使用に関する一般的な情報は、「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

11

Webサービス・クライアント・ファイルをコンパイルしてデプロイします。

適切なターゲットを呼び出してクライアント・ファイルをコンパイルし、ソースWebLogic Serverにデプロイします。例:

prompt> ant build-clientService deploy-clientService

12

Webサービスの信頼性のあるメッセージングを監視します。

WebLogic Server管理コンソールを使用して、Webサービスの信頼性のあるメッセージングを監視します。「Webサービスの信頼性のあるメッセージングの監視」を参照してください。

以降の項では、これらの各手順について詳細に説明します。さらに、次のトピックについて説明します。

- ビジネス作業単位へのメッセージのグループ化(バッチ化): メッセージをビジネス作業単位にグループ化し(バッチ化とも呼ばれます)、信頼性のあるメッセージングを使用するときのパフォーマンスを向上させます。

- 信頼性のあるWebサービスを再デプロイする際にクライアント側で考慮すべき事項: 信頼性のある更新済WebLogic Webサービスの新しいバージョンを、同じWebサービスの古いバージョンと一緒にデプロイする際に、クライアント側で考慮すべき事項について説明します。

- WebLogic Webサービスの信頼性のあるメッセージングとの相互運用性: WebLogic Webサービスの信頼性のあるメッセージングと相互運用するための推奨事項を示します。

送信元と宛先のWebLogic Serverインスタンスの構成

送信元と宛先のWebLogic Serverインスタンスに、Webサービスの永続性を構成する必要があります。信頼性のあるWebサービスを宛先WebLogic Serverインスタンスにデプロイし、信頼性のあるWebサービスを呼び出すクライアントを送信元WebLogic Serverインスタンスにデプロイします。

Webサービスの信頼性のあるメッセージングを使用するときは、状態が変化するたびに、Webサービスの信頼性のあるメッセージング・シーケンスがWebサービスの永続ストアに保存されます。状態変化の例を次に示します。

- 信頼性のあるメッセージングの状態が更新された(作成中、作成済み、終了中、終了済みなど)。

- セキュリティ・プロパティが更新された(セキュリティ・コンテキスト・トークンなど)。

- 信頼性のあるメッセージング・シーケンスでメッセージが送信された(メッセージ・バッファリングが有効の場合)。

- メッセージが到着したときに確認応答。

構成ウィザードでWebサービス固有の拡張テンプレートを使用してWebLogic Serverドメインを拡張することにより、Webサービスの永続性を構成できます。あるいは、Oracle WebLogic Server管理コンソールまたはWLSTを使用して、これらの高度な機能に必要なリソースを構成できます。Webサービス永続性の構成の詳細は、「Webサービス永続性の構成」を参照してください。

Webサービスにバッファリングを構成することもできます。メッセージ・バッファリングの構成に関する考慮事項と手順は、「第22章「Webサービスのためのメッセージ・バッファリングの構成」を参照してください。

Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成

WS-Policyファイルは、WS-Policy仕様に準拠するポリシー・アサーションを含むXMLファイルです。この場合、WS-PolicyファイルにはWebサービスの信頼性のあるメッセージングのポリシー・アサーションが含まれています。

WebLogic Serverには、標準的な信頼性のあるメッセージング・アサーションを含むWS-Policyファイルがあらかじめパッケージ化されています。独自のWS-Policyファイルを作成しない場合は、これらのファイルを使用できます。

次の表に、あらかじめパッケージ化されているWS-Policyファイルを示します。この表は、WS-Policyファイルをメソッド・レベルでアタッチできるかどうかも指定します。この列の値が「No」の場合、WS-Policyファイルをクラス・レベルでのみアタッチできます。詳細は、付録A「Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」を参照してください。

注意:
このリリースでは、DefaultReliability.xmlファイルとLongRunningReliability.xmlファイルは非推奨となっています。DefaultReliability1.2.xml、Reliability1.2_SequenceTransportSecurity、またはReliability1.0_1.2.xmlファイルを使用することをお薦めし、http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.2-spec-os.pdfであるWS-ReliableMessaging仕様の1.2バージョンに準拠する必要があります。

表14-7 信頼性のあるメッセージングをサポートする、あらかじめパッケージ化されているWS-Policyファイル

あらかじめパッケージ化されているWS-Policyファイル

説明

メソッド・レベルのアタッチ

DefaultReliability1.2.xml

配信保証に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702のWS Reliable Messaging Policy Assertion 1.2が基になっています。「DefaultReliability1.1.xml (WS-Policyファイル)」を参照してください。

はい

DefaultReliability1.1.xml

サービス品質に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。「DefaultReliability1.1.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.2_ExactlyOnce_WithMC1.1.xml

サービス品質に関するポリシー・アサーションを指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。「Reliability1.2_ExactlyOnce_WithMC1.1.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.2_SequenceSTRSecurity

信頼性のあるシーケンスでメッセージを保護するために、CreateSequenceメッセージで参照されるwsse:SecurityTokenReferenceをランタイムが使用するように指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702のWS Reliable Messaging Policy Assertion 1.2が基になっています。「Reliability1.2_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.1_SequenceSTRSecurity

Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。「Reliability1.1_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.2_SequenceTransportSecurity

トランスポート・レベルのセキュリティとサービス品質に関連するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702のWS Reliable Messaging Policy Assertion 1.2が基になっています。「Reliability1.2_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.1_SequenceTransportSecurity

トランスポート・レベルのセキュリティとサービス品質に関連するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。「Reliability1.1_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.0_1.2.xml

1.2と1.0のWS-Reliableメッセージング・ポリシー・アサーションを結合します。1.2バージョンのポリシー・アサーションはWebサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。このサンプルは、適切なポリシーの選択に基づいて実行時に適用されるポリシー・アサーションを決定します。「Reliability1.0_1.2.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.0_1.1.xml

1.1と1.0のWS Reliable Messagingポリシー・アサーションを結合します。「Reliability1.0_1.1.xml (WS-Policy.xmlファイル)」を参照してください。

はい

DefaultReliability.xml

非推奨。Webサービスの信頼性のあるメッセージングのアサーションは、WS Reliable Messaging Policy Assertion Version 1.0(http://schemas.xmlsoap.org/ws/2005/02/rm/WS-RMPolicy.pdf)に基づいています。このリリースでは、信頼性のあるメッセージングのポリシー・アサーションの多くが、JWSアノテーションまたは構成を通じて管理されます。

信頼性のあるメッセージングのポリシー・アサーションに一般的な値(非アクティブ・タイムアウト10分、確認応答の間隔200ミリ秒、基本的な再送信間隔3秒など)を指定します。「DefaultReliability.xml WS-Policyファイル(WS-Policy)[非推奨]」を参照してください。

はい

LongRunningReliability.xml

非推奨。長期実行プロセスに関して、Webサービスの信頼性のあるメッセージングのアサーションは、WS Reliable Messaging Policy Assertion Version 1.0に基づいています。このリリースでは、信頼性のあるメッセージングのポリシー・アサーションの多くが、JWSアノテーションまたは構成を通じて管理されます。

1つ前に示した、信頼性のあるメッセージングのデフォルトWS-Policyファイルとほぼ同じですが、アクティビティのタイムアウト間隔に、より大きな値(24時間)を指定する点が異なります。「LongRunningReliability.xml WS-Policyファイル(WS-Policy)[非推奨]」を参照してください。

はい

WebLogic Serverに含まれる、あらかじめパッケージ化されている信頼性のあるメッセージングWS-Policyファイルの1つを使用できます。これらのファイルは、ほとんどの場合に適合しています。あらかじめパッケージ化されているファイルは変更できません。値がニーズを満たさない場合は、カスタムのWS-Policyファイルを作成する必要があります。以下の節で、カスタムWS-Policyファイルの作成方法を説明します。

- WS-ReliableMessagingポリシー・アサーション・バージョン1.2と1.1を使用したカスタムWS-Policyファイルの作成

- WS-ReliableMessagingポリシー・アサーション・バージョン1.0を使用したカスタムWS-Policyファイルの作成(非推奨)

- 複数のポリシー選択肢の使用

WS-ReliableMessagingポリシー・アサーション・バージョン1.2と1.1を使用したカスタムWS-Policyファイルの作成

この項では、次の仕様に基づいたWebサービスの信頼性のあるメッセージングのアサーションを含むカスタムWS-Policyファイルを作成する方法について説明します。

- http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.2-spec-os.htmlのWS Reliable Messaging Policy Assertion Version 1.2

- http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion Version 1.1

WS-Policyファイルのルート要素は<Policy>であり、次のネームスペース宣言が含まれている必要があります。

<wsp:Policy
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">

Webサービスの信頼性のあるメッセージングのポリシー・アサーションはすべて、<wsrmp:RMAssertion>要素の内部でラップします。この要素には、Webサービスの信頼性のあるメッセージングのポリシー・アサーションを使用するため、次のネームスペース宣言が含まれている必要があります。

<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">

次の表に、WS-Policyファイルで指定可能なWebサービスの信頼性のあるメッセージングのアサーションを示します。アサーションの指定順序は重要です。次のアサーションを指定できますが、WS-Policyファイルでは次の一覧の順序どおりに指定する必要があります。

表14-8 Webサービスの信頼性のあるメッセージング・アサーション(バージョン1.2および1.1)

アサーション

説明

<wsrmp:SequenceSTR>

信頼性のあるシーケンスでメッセージを保護するため、ランタイムではCreateSequenceメッセージで参照されるwsse:SecurityTokenReferenceが使用されます。指定できるセキュリティ・アサーションは1つのみとなります。つまり、wsrmp:SequenceSTRまたはwsrmp:SequenceTransportSecurityのいずれか1つは指定できますが、両方は指定できません。

<wsrmp:SequenceTransportSecurity>

信頼性のあるシーケンスでメッセージを保護するため、ランタイムではCreateSequenceメッセージの送信に使用されるSSLトランスポート・セッションが使用されます。このアサーションは、特定のトランスポート・レベル・セキュリティ・メカニズム(sp:HttpsTokenなど)の使用を要求するsp:TransportBindingアサーションとともに使用する必要があります。指定できるセキュリティ・アサーションは1つのみとなります。つまり、wsrmp:SequenceSTRまたはwsrmp:SequenceTransportSecurityのいずれか1つは指定できますが、両方は指定できません。

<wsrm:DeliveryAssurance>

Webサービスの配信保証レベル(配信品質)。有効な値は、AtMostOnce、AtLeastOnce、ExactlyOnceおよびInOrder。次の表に定義されている配信保証のいずれか1つを設定できます。設定しない場合、配信保証にはデフォルトのExactlyOnceが使用されます。配信保証の詳細は、表14-1を参照してください。

次の例では、簡単なWebサービスの信頼性のあるメッセージングのWS-Policyファイルを示します。

<?xml version="1.0"?>

<wsp:Policy xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:SequenceTransportSecurity/>
<wsrmp:DeliveryAssurance>
<wsp:Policy>
<wsrmp:ExactlyOnce/>
</wsp:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp:Policy>

WS-Policyファイルにおける信頼性のあるメッセージングのポリシー・アサーションの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスの信頼性のあるメッセージングのポリシー・アサーションに関するリファレンスの項を参照してください。

WS-ReliableMessagingポリシー・アサーション・バージョン1.0を使用したカスタムWS-Policyファイルの作成(非推奨)

この項では、WS Reliable Messaging Policy Assertion Version 1.0(http://schemas.xmlsoap.org/ws/2005/02/rm/WS-RMPolicy.pdf)に基づいたWebサービスの信頼性のあるメッセージングのアサーションを含むカスタムWS-Policyファイルを作成する方法について説明します。

注意:
この項で説明されている信頼性のあるメッセージング・ポリシー・アサーションの多くは、JWSのアノテーションまたは構成を通じて管理されます。

WS-Policyファイルのルート要素は<Policy>です。Webサービスの信頼性のあるメッセージングのポリシー・アサーションを使用するには、これに次のネームスペース宣言が含まれていることが必要です。

<wsp:Policy
xmlns:wsrm="http://schemas.xmlsoap.org/ws/2005/02/rm"
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
xmlns:beapolicy="http://www.bea.com/wsrm/policy">

Webサービスの信頼性のあるメッセージングのポリシー・アサーションはすべて、<wsrm:RMAssertion要素の内部でラップします。wsrm:ネームスペースを使用するアサーションは、WS-ReliableMessaging仕様(http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.1-spec-os-01.pdf)で定義される標準的なアサーションです。beapolicy:ネームスペースを使用するアサーションは、WebLogic固有のものです。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスの信頼性のあるメッセージングのポリシー・アサーションに関するリファレンスの項を参照してください。

次の表に、WS-Policyファイルで指定可能なWebサービスの信頼性のあるメッセージングのアサーションを示します。Webサービスの信頼性のあるメッセージングのアサーションは、すべてオプションなので、デフォルト値が不適切なものだけを設定します。アサーションの指定順序は重要です。次のアサーションを指定できますが、WS-Policyファイルでは次の一覧の順序どおりに指定する必要があります。

表14-9 Webサービスの信頼性のあるメッセージング・アサーション(バージョン1.0)

アサーション

説明

<wsrm:InactivityTimeout>

非アクティブ間隔を定義する、Milliseconds属性で指定されるミリ秒数。この時間が経過した時点で、宛先エンドポイントがソース・エンドポイントからのメッセージを受け取っていなければ、宛先エンドポイントは、処理が行われずシーケンスは終了したものと見なす場合があります。これは、ソース・エンドポイントについても同様のことが言えます。デフォルトでは、シーケンスがタイムアウトすることはありません。

<wsrm:BaseRetransmissionInterval>

ソース・エンドポイントがメッセージを送信してから、そのメッセージの確認応答を受け取っていない場合に再送信を行うまでの間隔(ミリ秒単位)。デフォルト値は、ソース・エンドポイントのWebLogic Serverインスタンス上のSAFエージェントによって設定されます。

<wsrm:ExponentialBackoff>

再送信の間隔が、指数関数的なバックオフ・アルゴリズムを使用して調整されることを指定します。この要素には属性はありません。

<wsrm:AcknowledgmentInterval>

宛先エンドポイントがスタンドアロンの確認応答を送信する必要のある最大間隔(ミリ秒単位)。デフォルト値は、宛先エンドポイントのWebLogic Serverインスタンス上のSAFエージェントによって設定されます。

<beapolicy:Expires>

信頼性のあるWebサービスの有効期限が切れ、これ以上の新しいシーケンス・メッセージを受け付けなくなるまでの時間の長さ。デフォルト値では、有効期限が切れることはありません。この要素には、Expiresという1つの属性があります。この属性のデータ型はXMLスキーマ期間型です。(http://www.w3.org/TR/2001/REC-xmlschema-2-20010502/#durationを参照。)たとえば、有効期限までを1日と設定する場合は、<beapolicy:Expires Expires="P1D" />とします。

<beapolicy:QOS>

表14-1で説明されている、配信保証レベル。この要素にはQOSという1つの属性があり、この属性はAtMostOnce、AtLeastOnce、ExactlyOnceの各値のうちの1つに設定します。また、メッセージを順序通りにすることを指定するためにInOrder文字列を含めることもできます。デフォルト値はExactlyOnce InOrderです。この要素は通常、設定されません。

次の例では、簡単なWebサービスの信頼性のあるメッセージングのWS-Policyファイルを示します。

<?xml version="1.0"?>

<wsp:Policy
xmlns:wsrm="http://schemas.xmlsoap.org/ws/2005/02/rm/policy"
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
xmlns:beapolicy="http://www.bea.com/wsrm/policy"
>
<wsrm:RMAssertion>
<wsrm:InactivityTimeout
Milliseconds="600000" />
<wsrm:BaseRetransmissionInterval
Milliseconds="500" />
<wsrm:ExponentialBackoff />
<wsrm:AcknowledgementInterval
Milliseconds="2000" />
</wsrm:RMAssertion>
</wsp:Policy>

WS-Policyファイルにおける信頼性のあるメッセージングのポリシー・アサーションの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスの信頼性のあるメッセージングのポリシー・アサーションに関するリファレンスの項を参照してください。

複数のポリシー選択肢の使用

カスタム・ポリシー・ファイルを作成することによって、単一のWebサービスに対して複数のポリシー選択肢(適切なポリシー選択肢)を構成できます。実行時には、適用されるポリシーがそれらの中から自動的に選択されます。その際は、サポートされていないポリシーやアサーションが競合しているポリシーが除外され、構成されているプリファレンスに基づいて、受信メッセージの検証とレスポンス・メッセージの構築に適したポリシーが選択されます。

次の例では、1.2と1.0 WSの信頼性のあるメッセージングの両方をサポートするセキュリティ・ポリシーの例を示します。各ポリシー選択肢は、<wsp:All>要素で囲まれています。

注意:
1.0のWebサービスの信頼性のあるメッセージング・アサーションには、接頭辞としてwsrmp10が付加されます。

<wsp:Policy xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">
<wsp:ExactlyOne>
<wsp:All>
<wsrmp10:RMAssertion
xmlns:wsrmp10="http://schemas.xmlsoap.org/ws/2005/02/rm/policy">
<wsrmp10:InactivityTimeout Milliseconds="1200000"/>
<wsrmp10:BaseRetransmissionInterval Milliseconds="60000"/>
<wsrmp10:ExponentialBackoff/>
<wsrmp10:AcknowledgementInterval Milliseconds="800"/>
</wsrmp10:RMAssertion>
</wsp:All>
<wsp:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:SequenceSTR/>
<wsrmp:DeliveryAssurance>
<wsp:Policy>
<wsrmp:AtMostOnce/>
</wsp:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp:All>
</wsp:ExactlyOne>
</wsp:Policy>

複数のポリシー選択肢の詳細は、『Oracle WebLogic Server WebLogic Webサービスの保護』の適切なポリシーの選択に関する項を参照してください。

信頼性のあるJWSファイルに関するプログラミングのガイドライン

注意:
信頼性のあるWebサービスの開発に関するベスト・プラクティスについては、第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

信頼性のあるメッセージングのアサーションが含まれるWS-PolicyファイルをWebサービスに追加するよう指定するには、JWSファイルで@Policyアノテーションを使用します。WebLogic Serverでは、あらかじめパッケージ化されているWS-Policyファイルのセットが提供されます。付録A「Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」を参照してください。

Webサービスの信頼性のあるメッセージングで@Policyアノテーションを使用する場合は、次のガイドラインに従います。

- uri属性を使用して、ポリシー・ファイルのビルド時の場所を以下のように指定します。

- 独自のWS-Policyファイルを作成した場合は、JWSファイルを基準として相対的に場所を指定します。例:

@Policy(uri="ReliableHelloWorldPolicy.xml",
direction=Policy.Direction.both,
attachToWsdl=true)

この例では、ReliableHelloWorldPolicy.xmlファイルがJWSファイルと同じディレクトリに置かれています。

- あらかじめパッケージ化されているWS-Policyファイルの1つか、共有Java EEライブラリにパッケージ化されているWS-Policyファイルを指定するには、そのポリシー・ファイルの名前とパスとともにpolicy:接頭辞を使用します。この構文ではビルド時のjwsc Antタスクに、ファイル・システムの実際のファイルを探させず、Webサービスが、サービスのデプロイ時にWebLogic ServerからWS-Policyファイルを取得することを通知しています。

注意:
共有Java EEライブラリは、様々なエンタープライズ・アプリケーション内にパッケージ化されている複数のWebサービスとWS-Policyファイルを共有する場合に有用です。WS-Policyファイルが共有Java EEライブラリのMETA-INF/policiesまたはWEB-INF/policiesディレクトリに置かれているかぎり、ポリシー・ファイルはWebサービスの同じアーカイブにパッケージ化されている場合と同様に指定できます。ライブラリの作成、およびWebサービスがポリシー・ファイルを見つけることができるようにするための環境設定については、『Oracle WebLogic Serverアプリケーションの開発』の共有Java EEライブラリおよびオプション・パッケージの作成に関する項を参照してください。

- ポリシー・ファイルをWeb上で公開するよう指定するには、次の例に示すとおり、URLと共にhttp:接頭辞を使用します。

@Policy(uri="http://someSite.com/policies/mypolicy.xml"
direction=Policy.Direction.both,
attachToWsdl=true)

- デフォルトでは、WS-Policyファイルはリクエスト(インバウンド)とレスポンス(アウトバウンド)の両方のSOAPメッセージに適用されます。このデフォルトの動作は、direction属性をPolicy.Direction.inboundまたはPolicy.Direction.outboundに設定すると変更できます。

- uriで指定されるポリシー・ファイル内でwsp:optional属性を使用し、Webサービスで操作が確実に呼び出され、そのレスポンスが確実に配信されるよう要求するかどうかを指定できます。
次の点に注意してください。

- クライアントが同期トランスポートを使用してWebサービスを呼び出し、操作のインバウンド方向で信頼性が必要な場合は(optional属性がfalse)、クライアントは信頼性のあるレスポンスを送信する時使用できるようにofferシーケンスを提供する必要があります(http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.1-spec-os-01.pdfにあるWS-ReliableMessaging仕様で説明されている<wsrm: Offer...>)。

- クライアントが非同期トランスポートを使用する場合は、クライアントはofferシーケンスを送信する必要はありません。リクエストが信頼性を持って行われて、アウトバウンド方向にRMポリシーがある場合(オプションかどうか)信頼性のあるメッセージングのランタイムは、レスポンスをアウトバウンドするために新しいRMシーケンスのハンドシェイクを強制します。この新しいシーケンスはリクエスト・シーケンスと関連付けられ、それ以降のすべてのレスポンスは新しいレスポンス・シーケンスで送信されます。レスポンス・シーケンスは、リクエストのReplyToアドレスで示されているエンドポイントとネゴシエーションされます。

- @PolicyアノテーションのattachToWsdl属性を設定して、ポリシー・ファイルをWebサービスのパブリック規約が記述されたWSDLファイルに付加するかどうかを指定できます。通常は、クライアント・アプリケーションでWebサービスの信頼性のあるメッセージング機能が認識されるよう、パブリックなものとしてポリシーを公開します。そのため、この属性のデフォルト値はtrueです。

@Policyアノテーションの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のweblogic.jws.Policyに関する項を参照してください。

例14-1では、信頼性のあるWebサービスを実装する簡単なJWSファイルを示します。

例14-1 信頼性のあるWebサービスの例

import javax.jws.WebService;

import weblogic.jws.Policies;
import weblogic.jws.Policy;

/**
* Example web service for reliable client best practice examples
*/
@WebService
// Enable RM on this service.
@Policies( { @Policy(uri = "policy:DefaultReliability1.2.xml") })
public class BackendReliableService {

public String doSomething(String what) {

System.out.println("BackendReliableService doing: " + what);

return "Did (Reliably) '" + what + "' at: " + System.currentTimeMillis();
}
}

この例では、事前に定義されたDefaultReliability1.2.xmlポリシー・ファイルがクラス・レベルでWebサービスにアタッチされています。つまり、ポリシー・ファイルはWebサービスのすべてのパブリック操作(doSomething())に適用されます。ポリシー・ファイルは、デフォルトでリクエストとレスポンスの両方に適用されます。あらかじめパッケージ化されている利用可能なポリシーおよびカスタム・ポリシーの作成の詳細につぃては、「Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成」を参照してください。

Webサービス・クライアントからの信頼性のあるWebサービスの呼出し

注意:
信頼性のあるWebサービス・クライアントの開発に関するベスト・プラクティスについては、「信頼性のあるWebサービス・クライアントを開発するためのロードマップ」を参照してください。

次の表では、使用するトランスポート・タイプに基づいてWebサービス・クライアントから信頼性のあるWebサービスを呼び出す方法を示します。トランスポート・タイプの詳細は、表14-2を参照してください。

表14-10 トランスポート・タイプに基づく信頼性のあるWebサービスの呼出し

トランスポート・タイプ

説明

非同期トランスポート

非同期トランスポートを使用するには、次の手順を実行します:

1. Webサービス・クライアントを実装します(表12-3「非同期でWebサービスを呼び出すための手順」を参照)。
表12-3の手順3で、クライアントがファイアウォールの内側にあるかどうかに応じて、次のいずれかのトランスポート・メカニズムを実装します。

- 非同期クライアント・トランスポート機能(「スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)」を参照)。

- クライアントがファイアウォールの内側にある場合は接続作成(「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照)。

2. 同期または非同期の呼出しセマンティクスを使用して、Webサービスを呼び出します。
注意: 非同期クライアント・トランスポートまたは接続作成が有効になっているときは、同期操作を呼び出すことができます(「同期操作用の非同期クライアント・トランスポートの構成」および「同期メソッドのトランスポートとしての接続作成の構成」を参照)。

同期トランスポート

同期トランスポートを使用するには、標準のJAX-WS参照実装を使用して、信頼性のあるメッセージング・サービスのポート・インスタンスで非同期メソッドまたは同期メソッドを呼び出します(「JAX-WS参照実装の使用」を参照)。

注意: 同期トランスポートを使用してバッファ付きWebサービスを呼び出そうとした場合、結果は次のいずれかになります。

- シーケンスの最初のリクエストの場合、宛先のシーケンスはバッファなしに設定されます(Webサービスの構成がバッファなしとして設定されていた場合と同様)。

- シーケンスの最初のリクエストではない場合は(つまり、クライアントが前に非同期トランスポートを使用してリクエストを送信していた場合)、リクエストは破棄されてエラーが返されます。

クライアント側での追加の制御として、次のタスクを実行できます。

- クライアント側で信頼性のあるメッセージングを構成します(「信頼性のあるメッセージングの構成」を参照)。

- 信頼性のある配信が失敗した場合に通知を受け取る信頼性エラー・リスナーを実装します(「信頼性エラー・リスナーの実装」を参照)。ベスト・プラクティスとして信頼性エラー・リスナーを常に実装することをお薦めします。

- 構成オプションの設定、信頼性のあるシーケンスIDの取得、信頼性のあるシーケンスの終了など、信頼性のあるメッセージング・シーケンスに対する一般的なライフサイクル・タスクを実行します(「信頼性のあるメッセージ・シーケンスのライフサイクルの管理」を参照)。

信頼性のあるメッセージングの構成

注意:
信頼性のあるWebサービスの構成に関するベスト・プラクティスについては、第13章「信頼性のあるWebサービスとクライアントを開発するためのロードマップ」を参照してください。

WebLogic Server、Webサービス・エンドポイント、Webサービス・クライアントのレベルで、信頼性のあるWebサービスとクライアントのプロパティを構成できます。

WebLogic Serverレベルで定義したプロパティは、そのサーバーのすべての信頼性のあるWebサービスとクライアントに適用されます。WebLogic Serverレベルでの信頼性のあるメッセージングの構成の詳細は、「WebLogic Serverでの信頼性のあるメッセージングの構成」を参照してください。

必要がある場合は、次のようにして、サーバー・レベルで定義されている信頼性のあるメッセージングの構成オプションをオーバーライドできます。

- Webサービス・エンドポイント・レベルで、アプリケーション・デプロイメント・プランを更新します。デプロイメント・プランは、新しい値をアプリケーションの記述子内の特定の場所に関連付け、weblogic-webservices.xml記述子に保存されます。デプロイメント時に、デプロイメント・プランは変数割当ての値を、その変数のリンク先アプリケーション記述子内の場所に適用することによって、そのアプリケーション内の記述子に結合されます。詳細は、「Webサービス・エンドポイントでの信頼性のあるメッセージングの構成」を参照してください。

- Webサービスのクライアント・レベル。詳細は、「Webサービス・クライアントでの信頼性のあるメッセージングの構成」を参照してください。

次の項では、WebLogic Server、Webサービス・エンドポイント、Webサービス・クライアントの各レベルで信頼性のあるメッセージングを構成する方法を説明します。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

- Webサービス・クライアントでの信頼性のあるメッセージングの構成

- 基本の再送信間隔の構成

- 再送信間隔の指数関数的バックオフの構成

- 順序の有効期限の構成

- 非アクティブ・タイムアウトの構成

- Webサービスのバッファなし宛先の構成

- 確認応答の間隔の構成

- 信頼性エラー・リスナーの実装

WebLogic Serverでの信頼性のあるメッセージングの構成

WebLogic Serverでの信頼性のあるメッセージングは、WebLogic Server管理コンソールまたはWLSTを使用して構成できます。以降の項を参照してください。

- 管理コンソールの使用

- WLSTの使用

管理コンソールの使用

WebLogic Server管理コンソールを使用してWebLogic Serverに対して信頼性のあるメッセージングを構成するには、次の手順に従います。

1. 『Oracle WebLogic Server WebLogic Webサービスの理解』の管理コンソールの使用に関する項の説明に従って、WebLogic Server管理コンソールを呼び出します。

2. 左側のナビゲーション・ペインで、「環境」、「サーバー」の順に選択します。

3. 「構成」タブを選択し、「サーバー」表で、信頼性のあるメッセージングの構成の対象となるサーバーの名前をクリックします。

4. 「構成」タブ、「Webサービス」タブ、「信頼できるメッセージ」タブの順にクリックします。

5. 次の項の説明に従って、信頼性のあるメッセージングのプロパティを編集します。

- WebLogic ServerまたはWebサービス・エンドポイントでの基本の再送信間隔の構成

- WebLogic ServerまたはWebサービス・エンドポイントでの再送信間隔の指数関数的バックオフの構成

- WebLogic ServerまたはWebサービス・エンドポイントでの順序の有効期限の構成

- WebLogic ServerまたはWebサービス・エンドポイントでの非アクティブ・タイムアウトの構成

- Webサービスのバッファなし宛先の構成

- 確認応答の間隔の構成

6. 「保存」をクリックします。

詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービスの信頼性のあるメッセージングに関する項を参照してください。

WLSTの使用

または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

既定では、Webサービス・エンドポイントは、サーバーに対して定義されている信頼性のあるメッセージングの構成を使用します。次のようにすると、Webサービス・エンドポイントで使用される信頼性のあるメッセージングの構成を、WebLogic Server管理コンソールを使用してオーバーライドできます。

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. 『Oracle WebLogic Server WebLogic Webサービスの理解』の管理コンソールの呼出しに関する項の説明に従って、WebLogic Server管理コンソールを呼び出します。

2. 左側のナビゲーション・ペインで、「デプロイメント」を選択します。

3. 「デプロイメント」表でWebサービスの名前をクリックします。

4. 「構成」タブ、「ポート・コンポーネント」タブの順に選択します。

5. 「ポート」表でWebサービスのエンドポイントの名前をクリックします。

6. 「信頼できるメッセージ」タブを選択します。

7. 「信頼性のあるメッセージ構成のカスタマイズ」をクリックし、必要に応じて、指示に従ってデプロイメント・プランを保存します。

8. 次の項の説明に従って、信頼性のあるメッセージングのプロパティを編集します。

- WebLogic ServerまたはWebサービス・エンドポイントでの基本の再送信間隔の構成

- WebLogic ServerまたはWebサービス・エンドポイントでの再送信間隔の指数関数的バックオフの構成

- WebLogic ServerまたはWebサービス・エンドポイントでの順序の有効期限の構成

- WebLogic ServerまたはWebサービス・エンドポイントでの非アクティブ・タイムアウトの構成

- Webサービスのバッファなし宛先の構成

- 確認応答の間隔の構成

9. 「保存」をクリックします。

詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービスの信頼性のあるメッセージングの構成に関する項を参照してください。

Webサービス・クライアントでの信頼性のあるメッセージングの構成

Webサービス・クライアントでの信頼性のあるメッセージングの構成に関する一般的な情報は、「Webサービス・クライアントの構成」を参照してください。

Webサービスの信頼性のあるメッセージングのクライアントを作成するときのweblogic.wsee.reliability2.api.WsrmClientInitFeatureの使用の詳細は、次の項を参照してください。

- Webサービス・クライアントでの基本の再送信間隔の構成

- Webサービス・クライアントでの再送信間隔の指数関数的バックオフの構成

- Webサービス・クライアントでの順序の有効期限の構成

- Webサービス・クライアントでの非アクティブ・タイムアウトの構成

基本の再送信間隔の構成

ソース・エンドポイントが、指定された基本の再送信間隔内で所定のメッセージの確認応答を受信しなかった場合、ソース・エンドポイントはメッセージを再送信します。ソース・エンドポイントは、メッセージのシーケンスの存続期間内の任意の時点で、この再送信間隔を変更することがあります。

この間隔を再送信間隔の指数関数的バックオフ(「再送信間隔の指数関数的バックオフの構成」を参照)と組み合せて使用すると、再送信間隔を調整するアルゴリズムを指定できます。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP0DT5S (5秒)です。

次の項では、基本の再送信間隔を構成する方法について説明します。

- WebLogic ServerまたはWebサービス・エンドポイントでの基本の再送信間隔の構成

- Webサービス・クライアントでの基本の再送信間隔の構成

WebLogic ServerまたはWebサービス・エンドポイントでの基本の再送信間隔の構成

WebLogic Server管理コンソールを使用して、WebLogic ServerまたはWebサービス・エンドポイントのレベルで再送信間隔の指数関数的バックオフを構成するには、次の手順を実行します:

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. WebLogic Server管理コンソールを起動し、次の項の説明に従って、サーバー・レベルまたはWebサービス・エンドポイント・レベルで、Webサービスの信頼性のあるメッセージングのページにアクセスします。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

2. 必要に応じて、「基本の再送信間隔」の値を設定します。

Webサービス・クライアントでの基本の再送信間隔の構成

注意:
Webサービス・クライアントの構成の詳細は、「Webサービス・クライアントの構成」を参照してください。

表14-11では、メッセージをRM宛先に再送信する前に経過する必要のある時間を構成するためのweblogic.wsee.reliability2.api.WsrmClientInitFeatureメソッドについて説明します。

表14-11 基本の再送信間隔を構成するためのメソッド

メソッド

説明

String getBaseRetransmissionInterval()

基本の再送信間隔を取得します。

void setBaseRetransmissionInterval(String interval)

基本の再送信間隔を設定します。

次の例では、基本の再送信間隔を3時間に設定しています。

import java.xml.ws.WebService;
import java.xml.ws.WebServiceRef;
import wsrm_jaxws.example.client_service.*;
import wsrm_jaxws.example.client_service.EchoResponse;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;
...
@WebService
public class ClientServiceImpl {
...
@WebServiceRef(name="ReliableEchoService")
private ReliableEchoService service;
private ReliableEchoPortType port = null;
WsrmClientInitFeature initFeature = new WsrmClientInitFeature(true);
initFeature.setBaseRetransmissionInterval("P0DT3H");
port = service.getMyReliableServicePort(initFeature);
...

基本の再送信間隔の構成は、weblogic.xmlファイルでは次のように記述されます。

<service-reference-description>
...
<port-info>
<stub-property>
<name>weblogic.wsee.wsrm.BaseRetransmissionInterval</name>
<value>PT30S</value>
</stub-property>
...
</port-info>
</service-reference-description>

再送信間隔の指数関数的バックオフの構成

再送信間隔の指数関数的バックオフは、基本の再送信間隔(「基本の再送信間隔の構成」を参照)と組み合せて使用します。宛先エンドポイントが、基本の再送信間隔で指定した時間内にメッセージのシーケンスを確認応答しなかった場合、メッセージが引き続き確認されなければ、連続する再送信のタイミングに対して、送信元エンドポイントでは指数関数的バックオフ・アルゴリズムを使用します。

指数関数的なバックオフ・アルゴリズムは、連続再送信の間隔が、基本の再送信間隔を基に指数的に増えるように指定します。たとえば、基本の再送信間隔が2秒で、指数関数的なバックオフ要素が設定されている場合、連続再送信の間隔は、メッセージが確認されなければ、2、4、8、16、32秒というように増えていきます。

デフォルトではこのフラグは無効(false)であり、連続再送信の間隔は指数的に増えず、同じ値が維持されます。

次の項では、再送信間隔の指数関数的バックオフを構成する方法について説明します。

- WebLogic ServerまたはWebサービス・エンドポイントでの再送信間隔の指数関数的バックオフの構成

- Webサービス・クライアントでの再送信間隔の指数関数的バックオフの構成

WebLogic ServerまたはWebサービス・エンドポイントでの再送信間隔の指数関数的バックオフの構成

WebLogic Server管理コンソールを使用して、WebLogic ServerまたはWebサービス・エンドポイントのレベルで再送信間隔の指数関数的バックオフを構成するには、次の手順を実行します:

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. WebLogic Server管理コンソールを起動し、次の項の説明に従って、サーバー・レベルまたはWebサービス・エンドポイント・レベルで、Webサービスの信頼性のあるメッセージングのページにアクセスします。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

2. 必要に応じて、「再送信間隔の指数関数的バックオフの有効化」フラグを設定します。

Webサービス・クライアントでの再送信間隔の指数関数的バックオフの構成

注意:
Webサービス・クライアントの構成の詳細は、「Webサービス・クライアントの構成」を参照してください。

表14-12では、メッセージの再送信間隔を再送信間隔の指数関数的バックオフ・アルゴリズムを使用して調整するかどうかを構成するためのweblogic.wsee.reliability2.api.WsrmClientInitFeatureメソッドについて説明します。

表14-12 再送信間隔の指数関数的バックオフを構成するためのメソッド

メソッド

説明

Boolean isRetransmissionExponentialBackoff()

再送信間隔の指数関数的バックオフが有効かどうかを示します。

void setBaseRetransmissionExponentialBackoff(boolean value)

再送信間隔の指数関数的バックオフが有効かどうかを指定します。有効な値は、trueまたはfalseです。

次の例では、再送信間隔の指数関数的バックオフを有効にしています。

import java.xml.ws.WebService;
import java.xml.ws.WebServiceRef;
import wsrm_jaxws.example.client_service.*;
import wsrm_jaxws.example.client_service.EchoResponse;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;
...
@WebService
public class ClientServiceImpl {
...
@WebServiceRef(name="ReliableEchoService")
private ReliableEchoService service;
private ReliableEchoPortType port = null;
WsrmClientInitFeature initFeature = new WsrmClientInitFeature(true);
initFeature.setBaseRetransmissionInterval("P0DT3H");
initFeature.setBaseRetransmissionExponentialBackoff(true);
port = service.getMyReliableServicePort(initFeature);
...

再送信間隔の指数関数的バックオフの構成は、weblogic.xmlファイルでは次のように記述されます。

<service-reference-description>
...
<port-info>
<stub-property>
<name>weblogic.wsee.wsrm.RetransmissionExponentialBackoff</name>
<value>true</value>
</stub-property>
...
</port-info>
</service-reference-description>

順序の有効期限の構成

順序の有効期限は、アクティビティにかかわらず、シーケンスが期限切れになるまでの時間を指定します。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP1D (1日)です。

次の項では、順序の有効期限を構成する方法について説明します。

- WebLogic ServerまたはWebサービス・エンドポイントでの順序の有効期限の構成

- Webサービス・クライアントでの順序の有効期限の構成

WebLogic ServerまたはWebサービス・エンドポイントでの順序の有効期限の構成

WebLogic Server管理コンソールを使用して、WebLogic ServerまたはWebサービス・エンドポイントのレベルで順序の有効期限を構成するには、次の手順を実行します:

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. WebLogic Server管理コンソールを起動し、次の項の説明に従って、サーバー・レベルまたはWebサービス・エンドポイント・レベルで、Webサービスの信頼性のあるメッセージングのページにアクセスします。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

2. 必要に応じて、「順序の有効期限」の値を設定します。

Webサービス・クライアントでの順序の有効期限の構成

注意:
Webサービス・クライアントの構成の詳細は、「Webサービス・クライアントの構成」を参照してください。

表14-13では、アクティビティにかかわらず順序が期限切れになるまでの時間に対するweblogic.wsee.reliability2.api.WsrmClientInitFeatureメソッドについて説明します。

表14-13 順序の有効期限を構成するためのメソッド

メソッド

説明

String getSequenceExpiration()

現在構成されている順序の有効期限を返します。

void setSequenceExpiration(String expiration)

アクティビティにかかわらず、シーケンスが期限切れになるまでの時間。

次の例では、順序の有効期限を36時間に設定しています。

import java.xml.ws.WebService;
import java.xml.ws.WebServiceRef;
import wsrm_jaxws.example.client_service.*;
import wsrm_jaxws.example.client_service.EchoResponse;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;
...
@WebService
public class ClientServiceImpl {
...
@WebServiceRef(name="ReliableEchoService")
private ReliableEchoService service;
private ReliableEchoPortType port = null;
WsrmClientInitFeature initFeature = new WsrmClientInitFeature(true);
initFeature.setSequenceExpiration("P0DT36H");
port = service.getMyReliableServicePort(initFeature);
...

順序の有効期限の構成は、weblogic.xmlファイルでは次のように記述されます。

<service-reference-description>
...
<port-info>
<stub-property>
<name>weblogic.wsee.wsrm.SequenceExpiration</name>
<value>PT10M</value>
</stub-property>
...
</port-info>
</service-reference-description>

非アクティブ・タイムアウトの構成

非アクティブ・タイムアウト間隔内に、エンドポイント(RM送信元とRM宛先)がアプリケーションのメッセージまたはプロトコル・メッセージを受け取らなければ、エンドポイントはRMシーケンスが非アクティブなため終了したものと見なします。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP0DT600S (600秒)です。

次の項では、非アクティブ・タイムアウトを構成する方法について説明します。

- WebLogic ServerまたはWebサービス・エンドポイントでの非アクティブ・タイムアウトの構成

- Webサービス・クライアントでの非アクティブ・タイムアウトの構成

WebLogic ServerまたはWebサービス・エンドポイントでの非アクティブ・タイムアウトの構成

WebLogic Server管理コンソールを使用して、WebLogic ServerまたはWebサービス・エンドポイントのレベルで非アクティブ・タイムアウトを構成するには、次の手順を実行します:

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. WebLogic Server管理コンソールを起動し、次の項の説明に従って、サーバー・レベルまたはWebサービス・エンドポイント・レベルで、Webサービスの信頼性のあるメッセージングのページにアクセスします。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

2. 必要に応じて、「非アクティブ・タイムアウト」の値を設定します。

Webサービス・クライアントでの非アクティブ・タイムアウトの構成

注意:
Webサービス・クライアントの構成の詳細は、「Webサービス・クライアントの構成」を参照してください。

表14-14では、非アクティブ・タイムアウトを構成するためのweblogic.wsee.reliability2.api.WsrmClientInitFeatureメソッドについて説明します。

表14-14 非アクティブ・タイムアウトを構成するためのメソッド

メソッド

説明

String getInactivityTimeout()

現在構成されている非アクティブ・タイムアウトを返します。

void setInactivityTimeout(String timeout)

非アクティブ・タイムアウトを設定します。

次の例では、非アクティブ・タイムアウトを1時間に設定しています。

import java.xml.ws.WebService;
import java.xml.ws.WebServiceRef;
import wsrm_jaxws.example.client_service.*;
import wsrm_jaxws.example.client_service.EchoResponse;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;
...
@WebService
public class ClientServiceImpl {
...
@WebServiceRef(name="ReliableEchoService")
private ReliableEchoService service;
private ReliableEchoPortType port = null;
WsrmClientInitFeature initFeature = new WsrmClientInitFeature(true);
initFeature.setInactivityTimeout("P0DT1H");
port = service.getMyReliableServicePort(initFeature);
...

非アクティブ・タイムアウトの構成は、weblogic.xmlファイルでは次のように記述されます。

<service-reference-description>
...
<port-info>
<stub-property>
<name>weblogic.wsee.wsrm.InactivityTimeout</name>
<value>PT5M</value>
</stub-property>
...
</port-info>
</service-reference-description>

Webサービスのバッファなし宛先の構成

特定の宛先サーバーでメッセージ・バッファリングを無効にするかどうかを指定し、メッセージを受信するときにバッファリングを使用するかどうかを制御できます。宛先サーバーでバッファなしを構成できるのは、WebLogic ServerまたはWebサービス・エンドポイントのレベルのみであり、Webサービス・クライアントのレベルでは構成できません(Webサービス・クライアントではバッファリングがデフォルトで有効になります)。

注意:
バッファなし宛先を構成した場合、@WebServiceRefを使用して構成の参照を定義しているすべてのWebサービス・クライアントは、レスポンスをバッファリングなしで受け取ります。
バッファなし宛先の構成は、weblogic.xmlファイルでは次のように記述されます。

<service-reference-description>
...
<port-info>
<stub-property>
<name>weblogic.wsee.wsrm.NonBufferedDestination</name>
<value>true</value>
</stub-property>
...
</port-info>
</service-reference-description>

@WebServiceRefの詳細は、「@WebServiceRefアノテーションを使用したWebサービス参照の定義」を参照してください。

WebLogic Server管理コンソールを使用して、WebLogic ServerまたはWebサービス・エンドポイントのレベルで、メッセージのバッファリングを無効にするように宛先サーバーを構成するには、次の手順を実行します:

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. WebLogic Server管理コンソールを起動し、次の項の説明に従って、サーバー・レベルまたはWebサービス・エンドポイント・レベルで、Webサービスの信頼性のあるメッセージングのページにアクセスします。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

2. 必要に応じて、「非バッファ宛先」の値を設定し、宛先サーバーを構成します。

注意:
送信元サーバーでは、メッセージのバッファリングは常に有効にする必要があります。つまり、「非バッファ送信元」の値は常に無効にしておく必要があります。

確認応答の間隔の構成

確認応答の間隔では、宛先エンドポイントがスタンドアロンの確認応答を送信する必要のある最大間隔を指定します。確認応答の間隔を構成できるのはWebLogic ServerまたはWebサービス・エンドポイントのレベルのみであり、Webサービス・クライアントのレベルでは構成できません。

注意:
@WebServiceRefを使用してWebサービスへの参照を定義しているWebサービス・クライアントは、確認応答の間隔の値を使用して、クライアントのレスポンス処理が確認応答の受信を待機する時間を制御します。つまり、クライアントは、レスポンス・メッセージを受信するときにRM宛先と同じように動作します。
バッファなし宛先の構成は、weblogic.xmlファイルでは次のように記述されます。

<service-reference-description>
...
<port-info>
<stub-property>
<name>weblogic.wsee.wsrm.AcknowledgementInterval</name>
<value>PT5S</value>
</stub-property>
...
</port-info>
</service-reference-description>

@WebServiceRefの詳細は、「@WebServiceRefアノテーションを使用したWebサービス参照の定義」を参照してください。

宛先エンドポイントは、ソース・エンドポイントからメッセージを受信した直後に、返されたメッセージに対する確認応答を送信できます。また、スタンドアロンの確認応答として個別に確認応答を送信することもできます。返されたメッセージに対して確認応答を送信できない場合、宛先エンドポイントは、スタンドアロンの確認応答を送信するまで、確認応答の間隔に設定した時間範囲内で待機することがあります。未確認メッセージがない場合、宛先エンドポイントは確認応答を送信しない可能性があります。

指定する値は正の値とし、XMLスキーマの期間を表す字句形式、PnYnMnDTnHnMnSに従う必要があります。表14-15は、期間形式フィールドについて説明しています。この値のデフォルトはP0DT0.2S (0.2秒)です。

表14-15 期間形式の説明

フィールド

説明

nY

年数(n)

nM

月数(n)

nD

日数(n)

T

日付/時刻のセパレータ

nH

時間数(n)

nM

分数(n)

nS

秒数(n)

WebLogic Server管理コンソールを使用して、WebLogic ServerまたはWebサービス・エンドポイントのレベルで確認応答の間隔を構成するには、次の手順を実行します:

注意:
または、WLSTを使用して、信頼性のあるメッセージングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

1. WebLogic Server管理コンソールを起動し、次の項の説明に従って、サーバー・レベルまたはWebサービス・エンドポイント・レベルで、Webサービスの信頼性のあるメッセージングのページにアクセスします。

- WebLogic Serverでの信頼性のあるメッセージングの構成

- Webサービス・エンドポイントでの信頼性のあるメッセージングの構成

2. 必要に応じて、「確認応答の間隔」の値を設定します。

信頼性エラー・リスナーの実装

リクエストを配信できない場合に信頼性のある配信の障害に関する通知を受け取るには、次のweblogic.wsee.reliability2.api.ReliabilityErrorListenerインタフェースを実装します。

public interface ReliablityErrorListener {

public void onReliabilityError(ReliabilityErrorContext context);
}

表14-16では、信頼性エラー・リスナーを構成するためのweblogic.wsee.reliability2.api.WsrmClientInitFeatureメソッドについて説明します。

表14-16 信頼性エラー・リスナーを構成するためのメソッド

メソッド

説明

ReliabilityErrorListener getReliabilityListener()

現在構成されている信頼性リスナーを取得します。

void setErrorListener(ReliabilityErrorListener errorListener)

信頼性エラー・リスナーを設定します。

次の例では、Webサービス・クライアントに信頼性エラー・リスナーを実装して使用する方法を示します。この例は、例13-1「信頼性のあるWebサービス・クライアントのベスト・プラクティスの例」からの抜粋です。

import weblogic.wsee.reliability2.api.ReliabilityErrorListener;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;
...
@WebService
public class ClientServiceImpl {
...
WsrmClientInitFeature rmFeature = new WsrmClientInitFeature();
features.add(rmFeature);

ReliabilityErrorListener listener = new ReliabilityErrorListener() {
public void onReliabilityError(ReliabilityErrorContext context) {

// At a *minimum* do this
System.out.println("RM sequence failure: " +
context.getFaultSummaryMessage());
_lastResponse = context.getFaultSummaryMessage();

// And optionally do this...

// The context parameter tells you whether a request or the entire
// sequence has failed. If a sequence fails, you'll get a notification
// for each undelivered request (if any) on the sequence.
if (context.isRequestSpecific()) {
// We have a single request failure (possibly as part of a larger
// sequence failure).
// We can get the original request back like this:
String operationName = context.getOperationName();
System.out.println("Failed to deliver request for operation '" +
operationName + "'. Fault summary: " +
context.getFaultSummaryMessage());
if ("DoSomething".equals(operationName)) {
try {
String request = context.getRequest(JAXBContext.newInstance(),
String.class);
System.out.println("Failed to deliver request for operation '" +
operationName + "' with content: " +
request);
Map<String, Serializable> requestProps =
context.getUserRequestContextProperties();
if (requestProps != null) {
// Fetch back any property you sent in
// JAXWSProperties.PERSISTENT_CONTEXT when you sent the
// request.
String myProperty = (String)requestProps.get(MY_PROPERTY);
System.out.println(myProperty + " failed!");
}
} catch (Exception e) {
e.printStackTrace();
}
}
} else {
// The entire sequence has encountered an error.
System.out.println("Entire sequence failed: " +
context.getFaultSummaryMessage());

}
}
};

rmFeature.setReliabilityErrorListener(listener);

_features = features.toArray(new WebServiceFeature[features.size()]);

BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...

信頼性のあるメッセージ・シーケンスのライフサイクルの管理

WebLogic Serverでは、Webサービスの信頼性のあるメッセージングで使用するためのクライアントAPI weblogic.wsee.reliability2.api.WsrmClientが提供されています。このAPIを使用して、構成オプションの設定、信頼性のあるシーケンスIDの取得、信頼性のあるシーケンスの終了などの一般的なライフサイクル・タスクを実行します。

次に示すように、WsrmClient APIのインスタンスには、weblogic.wsee.reliability2.api.WsrmClientFactoryメソッドを使用して信頼性のあるWebサービス・ポートからアクセスできます。

package wsrm_jaxws.example;
import java.xml.ws.WebService;
import java.xml.ws.WebServiceRef;
import wsrm_jaxws.example.client_service.*;
import wsrm_jaxws.example.client_service.EchoResponse;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;
...
@WebService
public class ClientServiceImpl {
...
@WebServiceRef(name="ReliableEchoService")
private ReliableEchoService service;
private ReliableEchoPortType port = null;
port = service.getReliableEchoPort();
WsrmClient wsrmClient = WsrmClientFactory.getWsrmClientFromPort(port);
...

次の項では、WsrmClientを使用して信頼性のあるメッセージ・シーケンスのライフサイクルを管理する方法を説明します。

- 信頼性のあるシーケンスの管理

- クライアントIDの管理

- 確認応答済みリクエストの管理

- メッセージに関する情報へのアクセス

- 信頼性のあるシーケンスでの最後のメッセージの識別

- 信頼性のあるシーケンスを閉じる

- 信頼性のあるシーケンスの終了

- 新しいメッセージ・シーケンスを開始するためのクライアントのリセット

Webサービスの信頼性のあるメッセージング・クライアントAPIの詳細は、Oracle WebLogic Server Java APIリファレンスのweblogic.wsee.reliability2.api.WsrmClientに関する項を参照してください。

信頼性のあるシーケンスの管理

信頼性のあるシーケンスを管理するには、次のタスクを実行します。

- 信頼性のあるシーケンスIDを取得および設定します(「信頼性のあるシーケンスIDの取得および設定」を参照)。

- 信頼性のあるシーケンスの状態にアクセスし、たとえばアクティブかどうかや、終了されているかどうかなどを判定します(「信頼性のあるシーケンスの状態へのアクセス」を参照)。

信頼性のあるシーケンスIDの取得および設定

シーケンスIDは、特定の信頼性のあるシーケンスを識別するために使用されます。シーケンスIDの取得および設定は、それぞれ、weblogic.wsee.reliability2.api.WsrmClient.getSequenceID()メソッドおよびweblogic.wsee.reliability2.api.WsrmClient.setSequenceID()メソッドを使用します。getSequenceID()メソッドを発行した時点でメッセージが送信されていない場合、返される値はnullです。

例:

import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.api.WsrmClient;
...
_service = new BackendReliableServiceService();
...
features.add(... some features ...);
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...
WsrmClient rmClient = WsrmClientFactory.getWsrmClientFromPort(anotherPort);
...
// Will be null
String sequenceId = rmClient.getSequenceId();
// Send first message
anotherPort.doSomething("Bake a cake");
// Will be non-null
sequenceId = rmClient.getSequenceId();

サーバー障害からのリカバリ時には、新規作成したWebサービス上で信頼性のあるシーケンスを設定したり、クライアントまたはサーバーの再起動後にインスタンスをディスパッチしたりできます。クライアント・インスタンスのシーケンスIDの設定は高度な機能です。高度なクライアントは、setSequenceIdを使用してクライアント・インスタンスを既知のRMシーケンスに接続できます。

信頼性のあるシーケンスの状態へのアクセス

シーケンスの状態にアクセスするには、weblogic.wsee.reliability2.api.WsrmClient.getSequenceState()を使用します。このメソッドは、weblogic.wsee.reliability2.api.SequenceState型の定数java.lang.Enumを返します。

次の表では、シーケンスの状態に対して返される可能性のある有効な値を示します。

表14-17 シーケンスの状態の値

シーケンスの状態

説明

CLOSED

信頼性のあるシーケンスは閉じられています。

注意: シーケンスを閉じるのは、最後の手段と考える必要があり、すべてのリクエストを受信することがないと予想される信頼性のあるメッセージング・シーケンスを閉じる準備をするだけです。詳細は、「信頼性のあるシーケンスを閉じる」を参照してください。

CLOSING

信頼性のあるシーケンスは閉じられている途中です。

注意: シーケンスを閉じるのは、最後の手段と考える必要があり、すべてのリクエストを受信することがないと予想される信頼性のあるメッセージング・シーケンスを閉じる準備をするだけです。詳細は、「信頼性のあるシーケンスを閉じる」を参照してください。

CREATED

信頼性のあるシーケンスは作成されており、初期ハンドシェイクが完了しています。

CREATING

信頼性のあるシーケンスは作成されている途中であり、初期ハンドシェイクは進行中です。

LAST_MESSAGE

非推奨。WS-ReliableMessaging 1.0のみ。シーケンスの最後のメッセージを受信しました。

LAST_MESSAGE_PENDING

非推奨。WS-ReliableMessaging 1.0のみ。シーケンスの最後のメッセージは保留中です。

NEW

信頼性のあるシーケンスは初期状態です。初期ハンドシェイクは開始していません。

TERMINATED

信頼性のあるシーケンスは終了されました。

通常の処理では、最終メッセージまでのすべてのメッセージが確認応答された後は、信頼性のあるメッセージ・シーケンスは終了されます。お薦めはできませんが、信頼性のあるシーケンスを強制的に終了できます(「信頼性のあるシーケンスの終了」を参照)。

TERMINATING

信頼性のあるシーケンスは終了されている途中です。

通常の処理では、最終メッセージまでのすべてのメッセージが確認応答された後は、信頼性のあるメッセージ・シーケンスは終了されます。お薦めはできませんが、信頼性のあるシーケンスを強制的に終了できます(「信頼性のあるシーケンスの終了」を参照)。

例:

import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.api.WsrmClient;
import weblogic.wsee.reliability2.api.SequenceState;
...
_service = new BackendReliableServiceService();
...
features.add(... some features ...);
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...
WsrmClient rmClient = WsrmClientFactory.getWsrmClientFromPort(anotherPort);
...
SequenceState rmState = rmClient.getSequenceState();
if (rmState == SequenceState.TERMINATED) {
... Do some work or log a message ...
}
...

クライアントIDの管理

クライアントIDは、Webサービス・クライアントを示します。各クライアントは固有のIDを持っています。クライアントIDを使用して、クライアントまたはサーバーが再起動した後で信頼性のあるシーケンスに対して存在している可能性のある保存されたリクエストにアクセスできます。

クライアントIDは、WebLogic Serverによって自動的に構成されます。ポートを作成するときにweblogic.wsee.jaxws.persistence.ClientIdentityFeatureを使用して、クライアントIDをカスタム値に設定できます。詳細は、「クライアントIDの管理」を参照してください。

信頼性のあるメッセージングはクライアントIDを使用して、VMが再起動する前に送信されて、VMが終了する前に送信されなかったリクエストを発見します。以前のクライアントIDを使用して最初のクライアント・インスタンスを確立するとき、信頼性のあるメッセージングはそのポートと関連付けられているリソースを使用して、復元されたクライアントIDの代わりにリクエストの送信を開始します。

クライアントIDは、weblogic.wsee.reliability2.api.WsrmClient.getID()メソッドを使用して取得できます。

例:

import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.api.WsrmClient;
...
_service = new BackendReliableServiceService();
...
features.add(... some features ...);
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...
WsrmClient rmClient = WsrmClientFactory.getWsrmClientFromPort(anotherPort);
...
String clientId = rmClient.getId();
...

確認応答済みリクエストの管理

信頼性のあるメッセージ・シーケンスのライフサイクルの間に確認応答されたリクエストを表示するには、weblogic.wsee.reliability2.api.WsrmClient.ackRanges()メソッドを使用します。ackRanges()メソッドは、一連のweblogic.wsee.reliability.MessageRangeオブジェクトを返します。

確認応答が済んでいるリクエストの範囲を確認した後、クライアントは次を選択できます。

- weblogic.wsee.reliability2.api.WsrmClient.requestAcknowledgement()メソッドを使用して、RM宛先に確認応答リクエストを送信します。

- シーケンスを閉じ(「信頼性のあるシーケンスを閉じる」を参照)、特定の時間の後で確認応答されていないメッセージのアカウントに対してエラー処理を実行します。

注意: クライアントはgetAckRanges()を繰り返し呼び出して、信頼性のあるメッセージ・シーケンスを追跡できます。ただし、各呼出しにはある程度の追加オーバーヘッドが伴うことを考慮する必要があります。

メッセージに関する情報へのアクセス

weblogic.wsee.reliability2.api.WsrmClient.getMessageInfo()メソッドを使用すると、メッセージ番号に基づいて、クライアントから送信された信頼性のあるメッセージについての情報を取得できます。このメソッドは、クライアント・インスタンスから送信されたリクエスト・メッセージのシーケンシャル・メッセージ番号を表す長い値を受け取り、weblogic.wsee.reliability2.sequence.SourceMessageInfo型のメッセージに関する情報を返します。WsrmClient.getMostRecentMessageNumber()メソッドを使用すると、getMessageInfo()に渡すメッセージ番号の最大の値を特定できます。

返されるSourceMessageInfoオブジェクトは変更不可として扱う必要があり、getメソッドのみを使用する必要があります。

次の表では、送信元メッセージに関する特定の詳細にアクセスするために使用できるSourceMessageInfoメソッドの一覧を示します。

表14-18 SourceMessageInfo()のメソッド

メソッド

説明

getMessageID()

メッセージIDをString値として取得します。

getMessageNum()

メッセージの番号をlong値として取得します。

getResponseMessageInfo()

現在のSourceMessageInfo()オブジェクトによって表されるリクエストと関連付けられているレスポンスを表すweblogic.wsee.reliability2.sequence.DestinationMessageInfoオブジェクトを返します。このリクエストに対してレスポンスを受信していない場合、またはレスポンスが期待されない場合(たとえば、リクエストが一方向であった)は、NULLを返します。

isAck()

メッセージが確認応答されているかどうかを示します。

次の表では、宛先メッセージに関する特定の詳細にアクセスするために使用できるDestinationMessageInfoメソッドの一覧を示します。

表14-19 DestinationMessageInfo()のメソッド

メソッド

説明

getMessageID()

メッセージIDをString値として取得します。

getMessageNum()

メッセージの番号をlong値として取得します。

getMessageInfo()メソッドをweblogic.wsee.reliability2.api.WsrmClient.getMostRecentMessageNumber()と組み合わせて使用すると、最後に送信された信頼性のあるメッセージについての情報を取得できます。このメソッドは、1から始まり単調に増加するlong値を返します。次の状況では、このメソッドは-1を返します。

- 信頼性のあるシーケンスIDが設定されていない場合(getSequenceID()はnullを返します)。

- 最初の信頼性のあるメッセージがまだ送信されていません。

- 信頼性のあるシーケンスが終了されました。

信頼性のあるシーケンスでの最後のメッセージの識別

WebLogic Serverは信頼性のあるシーケンスと関連付けられたリソースを保持するので、適切なタイミングでこれらのリソースを解放することをお薦めします。通常の状況では、すべてのメッセージが送信され、RM宛先によって確認応答されるまで、信頼性のあるシーケンスを保持する必要があります。シーケンスの適切な終了を容易にするため、信頼性のあるメッセージ・シーケンスの最後のメッセージを識別することをお薦めします。これにより、RM宛先へのメッセージの送信が完了したことがわかり、WebLogic Serverは信頼性のあるシーケンスを自動的に終了する前に最後の確認応答の検索を開始できます。最後のメッセージを示すには、weblogic.wsee.reliability2.api.WsrmClient.setFinalMessage()メソッドを使用します。

最後のメッセージを識別すると、最後のメッセージまでのすべてのメッセージが確認応答され、信頼性のあるメッセージ・シーケンスが終了し、すべてのリソースが開放されます。そうでない場合、シーケンスは、構成したシーケンスの有効期限に達した後で自動的に終了します。

例:

import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.api.WsrmClient;
...
_service = new BackendReliableServiceService();
...
features.add(... some features ...);
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...
WsrmClient rmClient = WsrmClientFactory.getWsrmClientFromPort(anotherPort);
...
anotherPort.doSomething("One potato");
anotherPort.doSomething("Two potato");
anotherPort.doSomething("Three potato");
// Indicate this next invoke marks the 'final' message for the sequence
rmClient.setFinalMessage();
anotherPort.doSomething("Four");
...

信頼性のあるシーケンスを閉じる

信頼性のあるメッセージング・シーケンスを閉じるには、weblogic.wsee.reliability2.api.WsrmClient.closeMessage()を使用します。

注意:
このメソッドはWS-ReliableMessaging 1.1に対してのみ有効です。WS-ReliableMessaging 1.0ではサポートされていません。

信頼性のあるメッセージング・シーケンスを閉じると、新しいメッセージはRM宛先で受け付けられなくなり、RM送信元で送信されなくなります。閉じられたシーケンスは、まだ、RM宛先によって追跡され、確認応答リクエストに対応します。RM送信元は、シーケンスを終了する前に、信頼性のあるメッセージ・シーケンスの完全な会計情報を取得できます。

注意: シーケンスを閉じるのは、最後の手段と考える必要があり、すべてのリクエストを受信することがないと予想される信頼性のあるメッセージング・シーケンスを閉じる準備をするだけです。たとえば、確認応答が済んでいるリクエストの範囲を確認した後(「確認応答済みリクエストの管理」を参照)、クライアントはシーケンスを閉じる必要があると判断し、特定の時間の後で確認応答されていないメッセージのアカウントに対してエラー処理を実行できます。

信頼性のあるメッセージング・シーケンスが閉じられると、シーケンスの終了はクライアントに委ねられます。構成したタイムアウトに到達した後は、サーバーによって自動的に終了されなくなります。「信頼性のあるシーケンスの終了」を参照してください。

例:

import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.api.WsrmClient;
...
_service = new BackendReliableServiceService();
...
features.add(... some features ...);
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...
WsrmClient rmClient = WsrmClientFactory.getWsrmClientFromPort(anotherPort);
...
anotherPort.doSomething("One potato");
anotherPort.doSomething("Two potato");
// ... Wait some amount of time, and check for acks
// ... using WsrmClient.getAckRanges() ...
// ... If we don't find all of our acks ...
rmClient.closeSequence();
// ... Do some error recovery like telling our
// ... client we couldn't deliver all requests ...
rmClient.terminateSequence();
...

信頼性のあるシーケンスの終了

これはお薦めできませんが、weblogic.wsee.reliability2.api.WsrmClient.terminateSequence()メソッドを使用すると、すべてのメッセージが確認応答されているかどうかに関係なく、信頼性のあるメッセージ・シーケンスを終了できます。

注意:
代わりに、setFinalMessage()メソッドを使用して、信頼性のあるシーケンスの最後のメッセージを識別することをお薦めします。最後のメッセージを識別すると、最後のメッセージまでのすべてのメッセージが確認応答され、信頼性のあるメッセージ・シーケンスが終了し、すべてのリソースが開放されます。詳細は、「信頼性のあるシーケンスでの最後のメッセージの識別」を参照してください。

シーケンスを終了すると、RM送信元とRM宛先は、そのシーケンスに関連付けられているすべての状態を削除します。クライアントは、終了されたシーケンスに対してはいかなるアクションも実行できなくなります。シーケンスが終了されると、サーバー側の再試行(SAFエージェント)によってシーケンスに対して配信された保留中のリクエストは破棄され、ReliablityErrorListenerで通知として送信されます。

例:

import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.api.WsrmClient;
...
_service = new BackendReliableServiceService();
...
features.add(... some features ...);
_features = features.toArray(new WebServiceFeature[features.size()]);
...
BackendReliableService anotherPort =
_service.getBackendReliableServicePort(_features);
...
WsrmClient rmClient = WsrmClientFactory.getWsrmClientFromPort(anotherPort);
...
anotherPort.doSomething("One potato");
anotherPort.doSomething("Two potato");
// ... Wait some amount of time, and check for acks
// ... using WsrmClient.getAckRanges() ...
// ... If we don't find all of our acks ...
rmClient.closeSequence();
// ... Do some error recovery like telling our
// ... client we couldn't deliver all requests ...
rmClient.terminateSequence();
...

新しいメッセージ・シーケンスを開始するためのクライアントのリセット

信頼性のあるシーケンスが閉じられて、保持する必要のなくなった信頼性のあるメッセージングに関係のあるすべてのRequestContextプロパティをクリアするには、weblogic.wsee.reliability2.api.WsrmClient.reset()メソッドを使用します。通常、このメソッドは、同じクライアントから信頼性のあるメッセージの別のシーケンスを開始するときに呼び出します。

reset()の使用例については、例B-1「信頼性のあるメッセージングのバッチ化のためのクライアント・ラッパー・クラスの例」を参照してください。

Webサービスの信頼性のあるメッセージングの監視

WebLogic Server管理コンソールを使用して、Webサービスまたはクライアントの信頼性のあるメッセージング・シーケンスを監視できます。信頼性のあるメッセージングの順序ごとに、順序の状態、移行元サーバーおよび宛先サーバーなどの実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

具体的には、監視ページを使用して次のことを特定できます。

- 適切なタイミングでシーケンスをクリーンアップしているかどうか。監視タブに多数のシーケンスが表示される場合、クライアントのコードを調べて原因を特定します。

- 個別のシーケンスに確認応答されていないリクエストがあるか、または予想されるレスポンスを受信していないか。

Webサービスの信頼性のあるメッセージング・シーケンスを監視するには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表でWebサービスがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開すると、「Webサービス」カテゴリにアプリケーション内のWebサービスのリストが表示されます。Webサービス名をクリックし、「監視」→「ポート」→「信頼性のあるメッセージング」を選択します。

Webサービス・クライアントの信頼性のあるメッセージング・シーケンスを監視するには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表でWebサービス・クライアントがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開し、Webサービス・クライアントが存在するアプリケーション・モジュールをクリックします。「監視」タブ「Webサービス・クライアント」タブの順にクリックします。次に、「監視」→「サーバー」→「信頼性のあるメッセージング」をクリックします。

ビジネス作業単位へのメッセージのグループ化(バッチ化)

多くの場合、Webサービス・クライアントとサービスの間を流れるメッセージは、単一のビジネス・トランザクションつまり作業単位の一部です。たとえば、旅行代理店、航空会社、ホテル、レンタカー会社の間でメッセージを必要とする旅行代理店の予約処理などです。2つのエンドポイントの間を流れるすべてのメッセージはビジネス作業単位と考えることができます。

メッセージをRMシーケンスにグループ化することで、作業単位に関連のあるメッセージを処理するように信頼性のあるメッセージングを調整します。作業単位(つまりシーケンス)の全体がまとめて処理され、エラー・リカバリなどをシーケンス全体に適用できます(http://docs.oasis-open.org/ws-rx/wsrm/200702にあるWS-ReliableMessaging 1.2の仕様(2009年2月)でIncompleteSequenceBehavior要素の説明を参照)。たとえば、シーケンスのギャップの後で発生したリクエストを破棄したり、シーケンスから欠落したリクエストがある場合はリクエストのシーケンス全体を破棄したりするように、RMシーケンスを構成できます。

単位の最初のメッセージを送信する前に新しいクライアント・インスタンスを作成し、単位の最後のメッセージの後でクライアント・インスタンスを破棄することで、メッセージがビジネス作業単位の一部であることを示すことができます。または、WsrmClient API(クライアント・インスタンスをWsrmClientFactory.getWsrmClientFromPort()メソッドに渡すことで取得します)を使用して、シーケンス内の最後のリクエストが送信されようとしていることを示すことができます。これは、クライアント・インスタンスで呼出しを実行する直前にWsrmClient.setFinalMessage()を呼び出すことで行います(「信頼性のあるシーケンスでの最後のメッセージの識別」を参照)。

RMプロトコルには大きなオーバーヘッドが伴います。具体的には、シーケンスの作成と終了では、サービス(RM宛先)との間で往復メッセージが交換されます。つまり、RMシーケンスを確立して終了するには、4つのメッセージをやり取りする必要があります。このため、単一のRMシーケンス上の単一のビジネス作業単位内でリクエストを送信することには利点があります。これにより、RMプロトコルのオーバーヘッドのコストを複数のビジネス・メッセージに分割できます。

場合によっては、信頼性のあるサービスへの通信に使用されているクライアント・インスタンスは、メッセージの所属先のビジネス作業単位の固有概念がない環境で実行されます。その一例は、メッセージ・ブローカなどの仲介者です。この場合、ブローカは、メッセージ自体のみを認識し、メッセージが送信されているコンテキストを認識しないことがしばしばあります。ブローカは、ビジネス作業単位(またはシーケンス)の開始と終了の境界を定めるために何も実行しない場合があります。その結果、リクエストの送信に信頼性のあるメッセージングを使用するとき、ブローカは、送信するすべてのメッセージのRMシーケンス作成および終了プロトコルのオーバーヘッドを負担します。これは、パフォーマンスに重大な負の影響を及ぼす可能性があります。

組込みのビジネス作業単位がメッセージに対して不明の場合は、任意のグループ(バッチ)・メッセージを選択して、恣意的に作成した作業単位(バッチと呼ばれます)に含めることができます。信頼性のあるメッセージをバッチ化すると、前記のパフォーマンスに対する影響を回避でき、信頼性のあるメッセージングのクライアントとサービスの間のネットワーク使用とスループットを調整して最適化できます。関連のないリクエストを小さい単位(約10個のリクエスト)でバッチ化すると、クライアントとサービスの間のスループットが、信頼性のあるメッセージングを使用する(小さいメッセージを送信する)ときの3倍になる場合があることがテストにより示されました。

注意:
すでにビジネス作業単位と関連付けられているリクエストをバッチ化することはお薦めしません。これは、RMシーケンスの境界と作業単位の境界が一致しない場合、エラー・リカバリが複雑になる可能性があるためです。たとえば、ReliabilityErrorListenerを(WsrmClientInitFeatureを使用して)クライアント・インスタンスに追加すると(「信頼性エラー・リスナーの実装」を参照)、このリスナーを使用してシーケンス内の単一のリクエストまたはシーケンス全体の障害に対するエラー・リカバリを実行できます。リクエストをバッチ化する場合、リクエストの障害を適切に処理するために、各リクエストに関する何らかの情報を、このエラー・リカバリ・ロジックで格納する必要があります。バッチ化を行わないクライアントのほうが、それが属しているビジネス作業単位に基づいて、リクエストに関するコンテキストをより多く保持する可能性があります。

次のコード例では、RMリクエストのバッチ化を簡単かつ効率的にするために使用できるBatchingRmClientWrapperという名前のクラスの例を示します。このクラスは、リクエストを指定した数のリクエストのグループにバッチ化します。通常のクライアント・インスタンスに代わる動的なプロキシを作成できます。クライアント・インスタンスで呼び出すと、バッチ・ラッパーが発信リクエストをバッチにシームレスにグループ化し、各バッチに専用のRMシーケンスを割り当てます。バッチ・ラッパーは、特定のバッチの最大存続期間を示す期間指定も取得します。これにより、バッチを完全に満たすのに十分な発信リクエストがない場合でも、完了していないバッチを適切なタイミングで完了させることができます。バッチが指定されている最大存続期間のあいだ存在している場合、バッチの最後のメッセージが送信された場合と同じように閉じられます。

信頼性のあるメッセージングをバッチ化するために使用できるクライアント・ラッパー・クラスの例は、付録B「信頼性のあるメッセージングのバッチ化のためのクライアント・ラッパー・クラスの例」を参照してください。必要に応じてこのクラスをそのまま独自のアプリケーション・コードで使用できます。

例14-2 作業単位へのメッセージのグループ化の例(バッチ化)

import java.io.IOException;
import java.util.*;
import java.util.*;

import javax.servlet.*;
import javax.xml.ws.*;

import weblogic.jws.jaxws.client.ClientIdentityFeature;
import weblogic.jws.jaxws.client.async.AsyncClientHandlerFeature;
import weblogic.jws.jaxws.client.async.AsyncClientTransportFeature;
import weblogic.wsee.reliability2.api.ReliabilityErrorContext;
import weblogic.wsee.reliability2.api.ReliabilityErrorListener;
import weblogic.wsee.reliability2.api.WsrmClientInitFeature;

/**
* Example client for invoking a reliable web service and 'batching' requests
* artificially into a sequence. A wrapper class called
* BatchingRmClientWrapper is called to begin and end RM sequences for each batch of
* requests. This avoids per-message RM sequence handshaking
* and termination overhead (delivering better performance).
*/
public class BestPracticeAsyncRmBatchingClient
extends GenericServlet {

private BackendReliableServiceService _service;
private BackendReliableService _singletonPort;
private BackendReliableService _batchingPort;

private static int _requestCount;
private static String _lastResponse;

@Override
public void init()
throws ServletException {

_requestCount = 0;
_lastResponse = null;

// Only create the web service object once as it is expensive to create repeatedly.
if (_service == null) {
_service = new BackendReliableServiceService();
}

// Best Practice: Use a stored list of features, per client ID, to create client instances.
// Define all features for the web service port, per client ID, so that they are
// consistent each time the port is called. For example:
// _service.getBackendServicePort(_features);

List<WebServiceFeature> features = new ArrayList<WebServiceFeature>();

// Best Practice: Explicitly define the client ID.
ClientIdentityFeature clientIdFeature =
new ClientIdentityFeature("MyBackendServiceAsyncRmBatchingClient");
features.add(clientIdFeature);

// Best Practice: Always implement a reliability error listener.
// Include this feature in your reusable feature list. This enables you to determine
// a reason for failure, for example, RM cannot deliver a request or the RM sequence fails in
// some way (for example, client credentials refused at service).
WsrmClientInitFeature rmFeature = new WsrmClientInitFeature();
features.add(rmFeature);
rmFeature.setErrorListener(new ReliabilityErrorListener() {
public void onReliabilityError(ReliabilityErrorContext context) {
// At a *minimum* do this
System.out.println("RM sequence failure: " +
context.getFaultSummaryMessage());
_lastResponse = context.getFaultSummaryMessage();
}
});

// Asynchronous endpoint
AsyncClientTransportFeature asyncFeature =
new AsyncClientTransportFeature(getServletContext());
features.add(asyncFeature);

// Best Practice: Define a port-based asynchronous callback handler,
// AsyncClientHandlerFeature, for asynchronous and dispatch callback handling.
BackendReliableServiceAsyncHandler handler =
new BackendReliableServiceAsyncHandler() {
public void onDoSomethingResponse(Response<DoSomethingResponse> res) {
// ... Handle Response ...
try {
DoSomethingResponse response = res.get();
_lastResponse = response.getReturn();
System.out.println("Got reliable/async/batched response: " + _lastResponse);
} catch (Exception e) {
_lastResponse = e.toString();
e.printStackTrace();
}
}
};
AsyncClientHandlerFeature handlerFeature =
new AsyncClientHandlerFeature(handler);
features.add(handlerFeature);

// Set the features used when creating clients with
// this client ID "MyBackendServiceAsyncRmBatchingClient"

WebServiceFeature[] featuresArray =
features.toArray(new WebServiceFeature[features.size()]);

// Best Practice: Define a singleton port instance and initialize it when
// the client container initializes (upon deployment).
// The singleton port will be available for the life of the servlet.
// Creation of the singleton port triggers the asynchronous response endpoint to be published
// and it will remain published until our container (Web application) is undeployed.
// Note, we will get a call to destroy() before this.
_singletonPort = _service.getBackendReliableServicePort(featuresArray);

// Create a wrapper class to 'batch' messages onto RM sequences so
// a client with no concept of which messages are related as a unit can still achieve
// good performance from RM. The class will send a given number of requests on
// the same sequence, and then terminate that sequence before starting
// another to carry further requests. A batch has both a max size and
// lifetime so no sequence is left open for too long.
// The example batches 10 messages or executes for 20 seconds, whichever comes
// first. Assuming there were 15 total requests to send, the class would start and complete
// one full batch of 10 requests, then send the next batch of five requests.
// Once the batch of five requests has been open for 20 seconds, it will be closed and the
// associated sequence terminated (even though 10 requests were not sent to fill the batch).
BackendReliableService batchingPort =
_service.getBackendReliableServicePort(featuresArray);
BatchingRmClientWrapper<BackendReliableService> batchingSeq
= new BatchingRmClientWrapper<BackendReliableService>(batchingPort,
BackendReliableService.class,
10, "PT20S",
System.out);
_batchingPort = batchingSeq.createProxy();
}

@Override
public void service(ServletRequest req, ServletResponse res)
throws ServletException, IOException {

// TODO: ... Read the servlet request ...

// For this simple example, echo the _lastResponse captured from
// an asynchronous DoSomethingResponse response message.

if (_lastResponse != null) {
res.getWriter().write(_lastResponse);
System.out.println("Servlet returning _lastResponse value: " + _lastResponse);
_lastResponse = null; // Clear the response so we can get another
return;
}

// Synchronize on _batchingPort since it is a class-level variable and it might
// be in this method on multiple threads from the servlet engine.

synchronized(_batchingPort) {

// Use the 'batching' port to send the requests instead of creating a
// new request each time.
BackendReliableService port = _batchingPort;

// Set the endpoint address for BackendService.
((BindingProvider)port).getRequestContext().
put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"http://localhost:7001/BestPracticeReliableService/BackendReliableService");

// Make the invocation. Our asynchronous handler implementation (set
// into the AsyncClientHandlerFeature above) receives the response.
String request = "Protected and serve " + (++_requestCount);
System.out.println("Invoking DoSomething reliably/async/batched with request: " +
request);
port.doSomethingAsync(request);
}

// Return a canned string indicating the response was not received
// synchronously. Client needs to invoke the servlet again to get
// the response.
res.getWriter().write("Waiting for response...");
}

@Override
public void destroy() {

try {
// Best Practice: Explicitly close client instances when processing is complete.
// Close the singleton port created during initialization. Note, the asynchronous
// response endpoint generated by creating _singletonPort *remains*
// published until our container (Web application) is undeployed.
((java.io.Closeable)_singletonPort).close();
// Best Practice: Explicitly close client instances when processing is complete.
// Close the batching port created during initialization. Note, this will close
// the underlying client instance used to create the batching port.
((java.io.Closeable)_batchingPort).close();

// Upon return, the Web application is undeployed, and the asynchronous
// response endpoint is stopped (unpublished). At this point,
// the client ID used for _singletonPort will be unregistered and will no longer be
// visible from the Administration Console and WLST.
} catch (Exception e) {
e.printStackTrace();
}
}
}

信頼性のあるWebサービスを再デプロイする際にクライアント側で考慮すべき事項

WebLogic Serverでは、本番用の再デプロイメントがサポートされています。つまり、信頼性のあるWebLogic Webサービスの更新後の新しいバージョンを、同じWebサービスの古いバージョンと並行してデプロイできます。

WebLogic Serverでは、新しいクライアントのリクエストのみが新しいバージョンに転送されるように、クライアント接続が自動的に管理されます。再デプロイメント時にすでにWebサービスに接続していたクライアントは、作業が完了するまで古いバージョンのサービスを使用し続け、それらの作業が完了した時点で、WebLogic Serverが古いWebサービスを自動的にリタイアします。クライアントが信頼性のあるWebサービスに接続されている場合は、既存の信頼性のあるメッセージ・シーケンスがクライアントによって明示的に終了されるか、またはタイムアウトになったときに、そのクライアントの作業が完了したとみなされます。

本番用の再デプロイメントおよびWebサービス・クライアントの追加情報については、「Webサービスを再デプロイする際にクライアント側で考慮すべき事項」を参照してください。

WebLogic Webサービスの信頼性のあるメッセージングとの相互運用性

WebLogic Webサービスの信頼性のあるメッセージングの実装は、IBMおよびMicrosoft .NETの各サード・パーティ・ベンダーのWebサービスで提供されるWebサービスの信頼性のあるメッセージングの実装と相互運用できます。Microsoft .NETと相互運用するときのベスト・プラクティスは、『Oracle WebLogic Server WebLogic Webサービスの理解』のMicrosoft WCF/.NETとの相互運用性に関する項を参照してください。

Webサービスの信頼性のあるメッセージングを使用するOracle SOAサービスとの相互運用性を拡張するには、相互運用性に関する次のガイドラインを考慮してください。

- 非同期トランスポートには接続作成を使用しないでください(「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」を参照)。信頼性のあるSOAサービスは接続作成をサポートしません。

- WS-SecureConversationを使用して信頼性のあるWebサービスを保護しないでください。SOAサービスは、Webサービスの信頼性のあるメッセージングとWS-SecureConversationの併用をサポートしません。

- 信頼性のあるSOAサービスにアクセスする信頼性のあるWebLogic Webサービス・クライアントの場合:

- 同期(匿名WS-Addressing ReplyTo EPR)リクエスト応答または一方向MEP(メッセージ交換パターン)を使用します。

- 非同期(非匿名WS-Addressing ReplyTo EPR)リクエスト応答MEPは使用しないでください。

- 信頼性のあるWebLogic Webサービスにアクセスする信頼性のあるSOAクライアントの場合、次のいずれかを使用します。

- 同期(匿名WS-Addressing ReplyTo EPR)リクエスト応答または一方向MEP。

- 非同期(非匿名WS-Addressing ReplyTo EPR)リクエスト応答MEP。

15 Webサービス原子性トランザクションの使用

この章では、Java API for XML Web Services (JAX-WS)を使用したfor WebLogic Server 12.1.3用のWebLogic Webサービスで、Webサービス原子性トランザクションを使用して他の外部トランザクション処理システムとの相互運用性を実現する方法について説明します。

この章の内容は次のとおりです:

- Webサービス原子性トランザクションの概要

- Webサービスの高度な機能に必要なドメイン・リソースの構成

- Webサービスに対するWebサービス原子性トランザクションの有効化

- Webサービス・クライアントに対するWebサービス原子性トランザクションの有効化

- 管理コンソールを使用したWebサービス原子性トランザクションの構成

- クラスタ環境でのWebサービス原子性トランザクションの使用

- Webサービス原子性トランザクションのその他の使用例

Webサービス原子性トランザクションの概要

WebLogic Webサービスでは、次の仕様をサポートすることで、Websphere、Microsoft .NETといった他の外部トランザクション処理システムとの相互運用性を実現しています。

- Webサービスの原子性トランザクション(WS-AtomicTransaction)バージョン1.0、1.1、および1.2: http://docs.oasis-open.org/ws-tx/wstx-wsat-1.2-spec-cs-01/wstx-wsat-1.2-spec-cs-01.html

- Webサービスのコーディネーション(WS-Coordination)バージョン1.0、1.1、および1.2: http://docs.oasis-open.org/ws-tx/wstx-wscoor-1.2-spec-cs-01/wstx-wscoor-1.2-spec-cs-01.html

これらの仕様は、一連の参加者の間で分散されたアクティビティを調整するための拡張フレームワークを定義するものです。次の図に示されているコーディネータは中心的なコンポーネントで、トランザクションの状態(調整コンテキスト)を管理し、Webサービスおよびクライアントを参加者として登録することを可能にします。

図15-1 Webサービス原子性トランザクションのフレームワーク

次の表では、この図に示されているWebサービス原子性トランザクションのコンポーネントについて説明します。

表15-1 Webサービス原子性トランザクションのコンポーネント

コンポーネント

説明

コーディネータ

トランザクションの状態(調整コンテキスト)を管理し、Webサービスおよびクライアントを参加者として登録することを可能にします。

アクティブ化サービス

アプリケーションによるトランザクションのアクティブ化、およびアクティビティの調整コンテキストの作成を可能にします。作成された調整コンテキストは、トランザクション・フローとともに渡されます。

登録サービス

アプリケーションを参加者として登録することを可能にします。

アプリケーション・プロトコルX、Y

サポートされている調整プロトコル(WS-AtomicTransactionなど)。

次の図は、Webサービス原子性トランザクションのコンテキスト内で相互に作用する2つのWebLogic Serverインスタンスを示しています。わかりやすくするために、2つのWebLogic Webサービス・アプリケーションを示しています。

図15-2 WebLogic Server環境内のWebサービス原子性トランザクション

次の点に注意してください。

- ローカルJTAトランザクション・マネージャを使用すると、すべてWebサービス・リクエストのコンテキスト内で、トランザクションを下位トランザクションとしてローカルなJTA環境との間でインポートおよびエクスポートできます。

- 調整コンテキストの作成と管理は、ローカルJTAトランザクション・マネージャによって行われます。

- トランザクションの整合性管理とリカバリ処理はすべて、ローカルJTAトランザクション・マネージャによって行われます。

JTAの詳細は、『Oracle WebLogic Server JTAアプリケーションの開発』を参照してください。

次に、図15-2に示されているエンドツーエンドのWebサービス原子性トランザクションの相互作用の例について説明します。

1. アプリケーションAが、サーバーAでJTAトランザクション・マネージャを使用して、コントロールの現行スレッドに対するトランザクションを開始します。

2. アプリケーションAが、サーバーBのアプリケーションBでWebサービス・メソッドをコールします。

3. サーバーAがトランザクション情報を更新し、調整コンテキストを含むSOAPヘッダーを作成して、トランザクションおよびローカル・コーディネータを指定します。

4. サーバーBがアプリケーションBのリクエストを受信して、ヘッダーにトランザクション調整コンテキストが含まれていることを検出し、アプリケーションBがこのトランザクションの参加者としてすでに登録されているかどうかを判断します。すでに登録されていれば、そのトランザクションは再開され、登録されていない場合は、新しいトランザクションが開始されます。
アプリケーションBがインポート済トランザクションのコンテキスト内で実行されます。アプリケーションの対話に使用されるすべてのトランザクション・リソースは、このインポート済トランザクションに登録されます。

5. サーバーBが、トランザクション調整コンテキスト内で指定されている登録サービスを使用して、WS-AtomicTransactionトランザクションの参加者として自身を登録します。

6. サーバーAがトランザクションを再開します。

7. アプリケーションAが処理を再開し、トランザクションをコミットします。

Webサービスの高度な機能に必要なドメイン・リソースの構成

ドメインの作成または拡張を行う際に、Webサービス原子性トランザクションに加えて、Webサービスのその他の高度な機能を使用する予定の場合は(すぐに使用するのか、将来使用するのかを問わず)、WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を適用すると、Webサービスの高度な機能をサポートするのに必要なリソースを自動的に構成できます。この拡張テンプレートの使用は必須ではありませんが、使用すると必要なリソースの構成が格段に容易になります。あるいは、Oracle WebLogic Server管理コンソールまたはWLSTを使用して、これらの高度な機能に必要なリソースを構成できます。詳細は、「高度なWebサービス機能のためのドメインの構成」を参照してください。

注意:
Webサービスのその他の高度な機能をWebサービス原子性トランザクションとともに使用する予定がない場合、この拡張テンプレートを適用する必要はなく、起動時間とメモリー・フットプリントが最小限に抑えられます。

Webサービスに対するWebサービス原子性トランザクションの有効化

Webサービスに対してWebサービス原子性トランザクションを有効にするには:

- Javaから開始する場合(ボトムアップ)は、Webサービス・エンドポイントの実装クラスまたは実装メソッドに@weblogic.wsee.wstx.wsat.Transactionalアノテーションを追加します。詳細は、「JWSファイルでの@Transactionalアノテーションの使用」を参照してください。

- WSDから開始する場合(トップダウン)は、wsdlcを使用して既存のWSDLファイルからWebサービスを生成します。この場合、WSDLで通知されたWS-AtomicTransactionポリシー・アサーションが、wsdlcによって生成された新しいWebサービスのWSDLファイルに送られ、その中に組み込まれます。「WSDLから開始するWebサービス原子性トランザクションの有効化」を参照してください。

- デプロイメント時に、WebLogic Server管理コンソールを使用して、Webサービスのエンドポイント・レベルまたはメソッド・レベルでWebサービス原子性トランザクションを有効にして構成します。詳細は、「管理コンソールを使用したWebサービス原子性トランザクションの構成」を参照してください。

次の表は、Webサービス原子性トランザクションを有効にする際に設定可能な構成オプションをまとめたものです。

表15-2 Webサービス原子性トランザクションの構成オプション

属性

説明

Version

Webサービスおよびクライアントに対して使用されるWebサービス原子性トランザクション調整コンテキストのバージョン。クライアントの場合、アウトバウンド・メッセージに使用されるバージョンのみを指定します。指定した値は、トランザクション全体で整合性が取れている必要があります。

有効な値は、WSAT10、WSAT11、WSAT12、およびDEFAULTです。WebサービスのDEFAULT値は、3つのバージョンすべて(インバウンド・リクエストによって駆動される)であり、Webサービス・クライアントのDEFAULT値はWSAT10です。

Flow type

Webサービス原子性トランザクション調整コンテキストがトランザクション・フローとともに渡されるかどうか。有効な値は、表15-3を参照してください。

次の表は、フロー・タイプの有効な値と、Webサービスおよびクライアントでのそれらの意味をまとめたものです。この表では、@TransactionAttributeアノテーションを使用するEJB型のWebサービスに対してWebサービス原子性トランザクションを構成する際の有効な値の組合せも示しています。

表15-3 フロー・タイプの値

値

Webサービス・クライアント

Webサービス

EJB @TransactionAttributeの有効な値

NEVER

JTAトランザクションがある場合: トランザクションの調整コンテキストをエクスポートしません。

JTAトランザクションがない場合: トランザクションの調整コンテキストをエクスポートしません。

トランザクション・フローが存在する場合: トランザクションの調整コンテキストをインポートしません。CoordinationContextヘッダーにmustunderstand="true"が含まれている場合は、SOAPフォルトがスローされます。

トランザクション・フローがない場合: トランザクションの調整コンテキストをインポートしません。

NEVER、NOT_SUPPORTED、REQUIRED、REQUIRES_NEW、SUPPORTS

SUPPORTS (デフォルト)

JTAトランザクションがある場合: トランザクションの調整コンテキストをエクスポートします。

JTAトランザクションがない場合: トランザクションの調整コンテキストをエクスポートしません。

トランザクション・フローが存在する場合: トランザクション・コンテキストをインポートします。

トランザクション・フローがない場合: トランザクションの調整コンテキストをインポートしません。

REQUIRED、SUPPORTS

MANDATORY

JTAトランザクションがある場合: トランザクションの調整コンテキストをエクスポートします。

JTAトランザクションがない場合: 例外がスローされます。

トランザクション・フローが存在する場合: トランザクション・コンテキストをインポートします。

トランザクション・フローがない場合: サービス側の例外がスローされます。

MANDATORY、REQUIRED、SUPPORTS

JWSファイルでの@Transactionalアノテーションの使用

Webサービス原子性トランザクションを有効にするには、Webサービス・エンドポイントの実装クラスまたは実装メソッドに@weblogic.wsee.wstx.wsat.Transactionalアノテーションを指定します。

注意:
weblogic.jws.Transactionalもアノテーション付きのクラスまたは操作をトランザクション内で確実に実行するためのものですが、この場合のトランザクションは原子性トランザクションではありませんので、このアノテーションと混同しないでください。

次の点に注意してください。

- Webサービス・クラス・レベルで@Transactionalアノテーションを指定すると、サービス・エンドポイント・インタフェースで定義された双方向メソッドのすべてに設定が適用されます。フロー・タイプの値はメソッド・レベルでオーバーライドできますが、バージョンはトランザクション全体で一致している必要があります。

- @Onewayアノテーションも追加されているWebメソッドに対して、@Transactionalアノテーションを明示的に指定することはできません。

- Webサービス原子性トランザクションは、クライアント側の非同期プログラミング・モデルでは使用できません。

@Transactionalアノテーションを指定する際の形式は次のとおりです。

@Transactional(
version=Transactional.Version.[WSAT10|WSAT11|WSAT12|DEFAULT],
value=Transactional.TransactionFowType.[MANDATORY|SUPPORTS|NEVER]
)

バージョンおよびフロー・タイプの構成オプションの詳細は、表15-2を参照してください。

次の項では、@TransactionalアノテーションをWebサービスの実装クラス・レベルと実装メソッド・レベルで使用する例、およびEJB @TransactionAttributeアノテーションとともに使用する例を示します。

- 例: Webサービス・クラスでの@Transactionalアノテーションの使用

- 例: Webサービス・メソッドでの@Transactionalアノテーションの使用

- 例: @TransactionalアノテーションとEJB @TransactionAttributeアノテーションの併用

例: Webサービス・クラスでの@Transactionalアノテーションの使用

次の例は、@TransactionalアノテーションをWebサービス・クラスに追加する方法を示しています。関連するコードは太字で示されています。例に示すように、アクティブなJTAトランザクションがあります。

注意:
次のコードは、WebLogic Serverサンプル・サーバー付属のWebサービス原子性トランザクションの例から抜粋したものです。詳細は、「Webサービス原子性トランザクションのその他の使用例」を参照してください。

package examples.webservices.jaxws.wsat.simple.service;
. . .
import weblogic.jws.Policy;
import javax.transaction.UserTransaction;
. . .
import javax.jws.WebService;
import weblogic.wsee.wstx.wsat.Transactional;
import weblogic.wsee.wstx.wsat.Transactional.Version;
import weblogic.wsee.wstx.wsat.Transactional.TransactionFlowType;

/**
* This JWS file forms the basis of a WebLogic WS-Atomic Transaction Web Service with the
* operations: createAccount, deleteAccount, transferMonet, listAccount
*
*/

@WebService(serviceName = "WsatBankTransferService", targetNamespace = "http://tempuri.org/",
portName = "WSHttpBindingIService")
@Transactional(value=Transactional.TransactionFlowType.MANDATORY,
version=weblogic.wsee.wstx.wsat.Transactional.Version.WSAT10)
public class WsatBankTransferService {

public String createAccount(String acctNo, String amount) throws java.lang.Exception{
Context ctx = null;
UserTransaction tx = null;
try {
ctx = new InitialContext();
tx = (UserTransaction)ctx.lookup("javax.transaction.UserTransaction");
try {
DataSource dataSource = (DataSource)ctx.lookup("examples-demoXA-2");
String sql = "insert into wsat_acct_remote (acctno, amount) values (" + acctNo +
", " + amount + ")";
int insCount = dataSource.getConnection().prepareStatement(sql).executeUpdate();
if (insCount != 1)
throw new java.lang.Exception("insert fail at remote.");
return ":acctno=" + acctNo + " amount=" + amount + " creating. ";
} catch (SQLException e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new SQLException("SQL Exception during createAccount() at remote.");
}
} catch (java.lang.Exception e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new java.lang.Exception(e);
}
}
public String deleteAccount(String acctNo) throws java.lang.Exception{
...
}
public String transferMoney(String acctNo, String amount, String direction) throws
java.lang.Exception{
...
}
public String listAccount() throws java.lang.Exception{
...
}
}

例: Webサービス・メソッドでの@Transactionalアノテーションの使用

次の例は、@TransactionalアノテーションをWebサービス実装メソッドに追加する方法を示しています。関連するコードは太字で示されています。

package examples.webservices.jaxws.wsat.simple.service;
. . .
import weblogic.jws.Policy;
import javax.transaction.UserTransaction;
. . .
import javax.jws.WebService;
import weblogic.wsee.wstx.wsat.Transactional;
import weblogic.wsee.wstx.wsat.Transactional.Version;
import weblogic.wsee.wstx.wsat.Transactional.TransactionFlowType;

/**
* This JWS file forms the basis of a WebLogic WS-Atomic Transaction Web Service with the
* operations: createAccount, deleteAccount, transferMonet, listAccount
*
*/

@WebService(serviceName = "WsatBankTransferService", targetNamespace = "http://tempuri.org/",
portName = "WSHttpBindingIService")
public class WsatBankTransferService {

@Transactional(value=Transactional.TransactionFlowType.MANDATORY,
version=weblogic.wsee.wstx.wsat.Transactional.Version.WSAT10)
public String createAccount(String acctNo, String amount) throws java.lang.Exception{
Context ctx = null;
UserTransaction tx = null;
try {
ctx = new InitialContext();
tx = (UserTransaction)ctx.lookup("javax.transaction.UserTransaction");
try {
DataSource dataSource = (DataSource)ctx.lookup("examples-demoXA-2");
String sql = "insert into wsat_acct_remote (acctno, amount) values (" + acctNo +
", " + amount + ")";
int insCount = dataSource.getConnection().prepareStatement(sql).executeUpdate();
if (insCount != 1)
throw new java.lang.Exception("insert fail at remote.");
return ":acctno=" + acctNo + " amount=" + amount + " creating. ";
} catch (SQLException e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new SQLException("SQL Exception during createAccount() at remote.");
}
} catch (java.lang.Exception e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new java.lang.Exception(e);
}
}
public String deleteAccount(String acctNo) throws java.lang.Exception{
...
}
public String transferMoney(String acctNo, String amount, String direction) throws
java.lang.Exception{
...
}
public String listAccount() throws java.lang.Exception{
...
}
}

例: @TransactionalアノテーションとEJB @TransactionAttributeアノテーションの併用

次の例は、@TransactionalアノテーションとEJB @TransactionAttributeアノテーションを併用する方法を示しています。この場合、フロー・タイプの値に互換性があることが必要です(表15-3を参照)。関連するコードは太字で示されています。

package examples.webservices.jaxws.wsat.simple.service;
. . .
import weblogic.jws.Policy;
import javax.transaction.UserTransaction;
. . .
import javax.jws.WebService;
import javax.ejb.TransactionAttribute;
import javax.ejb.TransactionAttributeType;
import weblogic.wsee.wstx.wsat.Transactional;
import weblogic.wsee.wstx.wsat.Transactional.Version;
import weblogic.wsee.wstx.wsat.Transactional.TransactionFlowType;

/**
* This JWS file forms the basis of a WebLogic WS-Atomic Transaction Web Service with the
* operations: createAccount, deleteAccount, transferMonet, listAccount
*
*/

@WebService(serviceName = "WsatBankTransferService", targetNamespace = "http://tempuri.org/",
portName = "WSHttpBindingIService")
@Transactional(value=Transactional.TransactionFlowType.MANDATORY,
version=weblogic.wsee.wstx.wsat.Transactional.Version.WSAT10)
@TransactionAttribute(TransactionAttributeType.REQUIRED
public class WsatBankTransferService {
. . .
}

WSDLから開始するWebサービス原子性トランザクションの有効化

Webサービス原子性トランザクションは、有効にすると、ポリシー・アサーションを使用してWSDLファイルで通知されます。

表15-4は、Webサービス原子性トランザクションのフロー・タイプとEJBトランザクション属性との一般的な組合せに対応するWS-AtomicTransaction 1.2ポリシー・アサーションをまとめたものです。他のすべての組合せではビルド時にエラーが発生します。

表15-4 Webサービス原子性トランザクションのポリシー・アサーションの値(WS-AtomicTransaction 1.2)

原子性トランザクションのフロー・タイプ

EJB @TransactionAttribute

WS-AtomicTransaction 1.2ポリシー・アサーション

MANDATORY

MANDATORY、REQUIRED、SUPPORTS

<wsat:ATAssertion/>

SUPPORTS

REQUIRED、SUPPORTS

<wsat:ATAssertion wsp:Optional="true"/>

NEVER

REQUIRED、REQUIRES_NEW、NEVER、SUPPORTS、NOT_SUPPORTED

ポリシーの通知なし

wsdlc Antタスクを使用すると、既存のWSDLファイルから一連のアーティファクトを生成し、それをまとめて、WSDLファイルに記述されたWebサービスの部分的なJava実装を提供することができます。WSDLファイルで通知されたWS-AtomicTransactionポリシー・アサーションは、wsdlcによって生成された新しいWebサービスのWSDLファイルに送られ、その中に組み込まれます。

wsdlc Antタスクでは、生成されたJWSインタフェースの部分的な(途中まで作成済の)実装を含むJWSファイルが生成されます。このファイルを変更してビジネス・コードを組み込む必要があります。ビジネス・ロジックを含むJWSファイルをコーディングしたら、jwsc Antタスクを実行して、Webサービスの完全なJava実装を生成します。wsdlc Antタスクによって生成されたJARファイル(JWSインタフェース・ファイルとデータ・バインディング・アーティファクトを含む)を指定するには、jwscのcompiledWsdl属性を使用します。この属性を指定した場合、jwsc Antタスクでは新しいWSDLファイルが生成されるかわりに、JARファイル内のWSDLファイルが使用されます。そのため、WebサービスをデプロイしてそのWSDLを参照すると、デプロイ済のWSDLは開始当初のWSDLとまったく同じように見えます(WS-AtomicTransactionポリシー・アサーションが付いています)。

wsdlcを使用した、WSDLファイルからのWebサービスの生成の詳細は、「WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順」を参照してください。

Webサービス・クライアントに対するWebサービス原子性トランザクションの有効化

Webサービス・クライアントに対しては、次のいずれかの方法でWebサービス原子性トランザクションを有効にします。

- クライアントのWebサービス参照インジェクション・ポイントに@weblogic.wsee.wstx.wsat.Transactionalアノテーションを追加します。詳細は、「@Transactionalアノテーションと@WebServiceRefアノテーションの併用」を参照してください。

- Webサービスのプロキシまたはディスパッチの作成時にweblogic.wsee.wstx.wsat.TransactionalFeatureのインスタンスをパラメータとして渡します。詳細は、「TransactionalFeatureをクライアントに渡す」を参照してください。

- デプロイメント時に、WebLogic Server管理コンソールを使用して、Webサービス・クライアントのエンドポイント・レベルまたはメソッド・レベルでWebサービス原子性トランザクションを有効にして構成します。詳細は、「管理コンソールを使用したWebサービス原子性トランザクションの構成」を参照してください。

- 実行時に、原子性トランザクションに対応していないWebサービス・クライアントが。原子性トランザクションに対応しているWebサービスを呼び出すと、WSDLで示されるフロー・タイプの設定に基づいて次の処理が行われます。

- サービス側でフロー・タイプがSUPPORTSまたはNEVERに設定されている場合、呼出しはトランザクションの一部として組み込まれます。

- フロー・タイプがMANDATORYに設定されている場合、例外がスローされます。

Webサービス原子性トランザクションを有効にする際に設定可能な構成オプションについては、表15-2を参照してください。

@Transactionalアノテーションと@WebServiceRefアノテーションの併用

Webサービス原子性トランザクションを有効にするには、Webサービス・クライアントのWebサービス参照(@WebServiceRef)インジェクション・ポイントに@weblogic.wsee.wstx.wsat.Transactionalアノテーションを指定します。

@Transactionalアノテーションを指定する際の形式は次のとおりです。

@Transactional(
version=Transactional.Version.[WSAT10|WSAT11|WSAT12|DEFAULT],
value=Transactional.TransactionFlowType.[MANDATORY|SUPPORTS|NEVER]
)

バージョンおよびフロー・タイプの構成オプションの詳細は、表15-2を参照してください。

次の例は、Webサービス参照インジェクション・ポイントにアノテーションを追加する方法を示しています。関連するコードは太字で示されています。例に示すように、アクティブなJTAトランザクションは原子性トランザクションの一部になります。

注意:
次のコードは、WebLogic Serverサンプル・サーバー付属のWebサービス原子性トランザクションの例から抜粋したものです。詳細は、「Webサービス原子性トランザクションのその他の使用例」を参照してください。

package examples.webservices.jaxws.wsat.simple.client;
. . .
import javax.servlet.*;
import javax.servlet.http.*;
. . .
import java.net.URL;
import javax.xml.namespace.QName;

import javax.transaction.UserTransaction;
import javax.transaction.SystemException;

import javax.xml.ws.WebServiceRef;
import weblogic.wsee.wstx.wsat.Transactional;
*/

/**
* This example demonstrates using a WS-Atomic Transaction to create or delete an account,
* or transfer money via web service as a single atomic transaction.
*/

public class WsatBankTransferServlet extends HttpServlet {
. . .
String url = "http://localhost:7001";
URL wsdlURL = new URL(url + "/WsatBankTransferService/WsatBankTransferService");
. . .
DataSource ds = null;
UserTransaction utx = null;

try {
ctx = new InitialContext();
utx = (UserTransaction) ctx.lookup("javax.transaction.UserTransaction");
utx.setTransactionTimeout(900);
} catch (java.lang.Exception e) {
e.printStackTrace();
}

WsatBankTransferService port = getWebService(wsdlURL);

try {
utx.begin();
if (remoteAccountNo.length() > 0) {
if (action.equals("create")) {
result = port.createAccount(remoteAccountNo, amount);
} else if (action.equals("delete")) {
result = port.deleteAccount(remoteAccountNo);
} else if (action.equals("transfer")) {
result = port.transferMoney(remoteAccountNo, amount, direction);
}
}
utx.commit();
result = "The transaction is committed " + result;
} catch (java.lang.Exception e) {
try {
e.printStackTrace();
utx.rollback();
result = "The transaction is rolled back.    " + e.getMessage();
} catch(java.lang.Exception ex) {
e.printStackTrace();
result = "Exception is caught. Check stack trace.";
}
}
request.setAttribute("result", result);
. . .
@Transactional(value = Transactional.TransactionFlowType.MANDATORY,
version = Transactional.Version.WSAT10)
@WebServiceRef(wsdlLocation =
"http://localhost:7001/WsatBankTransferService/WsatBankTransferService?WSDL", value =
examples.webservices.jaxws.wsat.simple.service.WsatBankTransferService.class)
WsatBankTransferService_Service service;
private WsatBankTransferService getWebService() {
return service.getWSHttpBindingIService();
}

public String createAccount(String acctNo, String amount) throws java.lang.Exception{
Context ctx = null;         UserTransaction tx = null;
try {
ctx = new InitialContext();
tx = (UserTransaction)ctx.lookup("javax.transaction.UserTransaction");
try {
DataSource dataSource = (DataSource)ctx.lookup("examples-dataSource-demoXAPool");
String sql = "insert into wsat_acct_local (acctno, amount) values (
" + acctNo + ", " + amount + ")";
int insCount = dataSource.getConnection().prepareStatement(sql).executeUpdate();
if (insCount != 1)
throw new java.lang.Exception("insert fail at local.");
return ":acctno=" + acctNo + " amount=" + amount + " creating.. ";
} catch (SQLException e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new SQLException("SQL Exception during createAccount() at local.");
}
} catch (java.lang.Exception e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new java.lang.Exception(e);
}
}

public String deleteAccount(String acctNo) throws java.lang.Exception{
. . .
}
public String transferMoney(String acctNo, String amount, String direction) throws
java.lang.Exception{
. . .
}
public String listAccount() throws java.lang.Exception{
. . .
}
}

TransactionalFeatureをクライアントに渡す

Webサービスのクライアントに対してWebサービス原子性トランザクションを有効にするには、次の例のように、Webサービスのプロキシまたはディスパッチの作成時にweblogic.wsee.wstx.wsat.TransactionalFeatureのインスタンスをパラメータとして渡します。関連するコードは太字で示されています。

注意:
次のコードは、WebLogic Serverサンプル・サーバー付属のWebサービス原子性トランザクションの例から抜粋したものです。詳細は、「Webサービス原子性トランザクションのその他の使用例」を参照してください。

package examples.webservices.jaxws.wsat.simple.client;
. . .
import javax.servlet.*;
import javax.servlet.http.*;
. . .
import java.net.URL;
import javax.xml.namespace.QName;

import javax.transaction.UserTransaction;
import javax.transaction.SystemException;

import weblogic.wsee.wstx.wsat.TransactionalFeature;
import weblogic.wsee.wstx.wsat.Transactional.Version;
import weblogic.wsee.wstx.wsat.Transactional.TransactionFlowType;
*/

/**
* This example demonstrates using a WS-Atomic Transaction to create or delete an account,
* or transfer money via web service as a single atomic transaction.
*/

public class WsatBankTransferServlet extends HttpServlet {
. . .
String url = "http://localhost:7001";
URL wsdlURL = new URL(url + "/WsatBankTransferService/WsatBankTransferService");
. . .
DataSource ds = null;
UserTransaction utx = null;

try {
ctx = new InitialContext();
utx = (UserTransaction) ctx.lookup("javax.transaction.UserTransaction");
utx.setTransactionTimeout(900);
} catch (java.lang.Exception e) {
e.printStackTrace();
}

WsatBankTransferService port = getWebService(wsdlURL);

try {
utx.begin();
if (remoteAccountNo.length() > 0) {
if (action.equals("create")) {
result = port.createAccount(remoteAccountNo, amount);
} else if (action.equals("delete")) {
result = port.deleteAccount(remoteAccountNo);
} else if (action.equals("transfer")) {
result = port.transferMoney(remoteAccountNo, amount, direction);
}
}
utx.commit();
result = "The transaction is committed " + result;
} catch (java.lang.Exception e) {
try {
e.printStackTrace();
utx.rollback();
result = "The transaction is rolled back.    " + e.getMessage();
} catch(java.lang.Exception ex) {
e.printStackTrace();
result = "Exception is caught. Check stack trace.";
}
}
request.setAttribute("result", result);
. . .
// Passing the TransactionalFeature to the Client
private WsatBankTransferService getWebService(URL wsdlURL) {
TransactionalFeature feature = new TransactionalFeature();
feature.setFlowType(TransactionFlowType.MANDATORY);
feature.setVersion(Version.WSAT10);
WsatBankTransferService_Service service = new WsatBankTransferService_Service(wsdlURL,
new QName("http://tempuri.org/", "WsatBankTransferService"));
return service.getWSHttpBindingIService(new javax.xml.ws.soap.AddressingFeature(),
feature);
}

public String createAccount(String acctNo, String amount) throws java.lang.Exception{
Context ctx = null;         UserTransaction tx = null;
try {
ctx = new InitialContext();
tx = (UserTransaction)ctx.lookup("javax.transaction.UserTransaction");
try {
DataSource dataSource = (DataSource)ctx.lookup("examples-dataSource-demoXAPool");
String sql = "insert into wsat_acct_local (acctno, amount) values (
" + acctNo + ", " + amount + ")";
int insCount = dataSource.getConnection().prepareStatement(sql).executeUpdate();
if (insCount != 1)
throw new java.lang.Exception("insert fail at local.");
return ":acctno=" + acctNo + " amount=" + amount + " creating.. ";
} catch (SQLException e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new SQLException("SQL Exception during createAccount() at local.");
}
} catch (java.lang.Exception e) {
System.out.println("**** Exception caught *****");
e.printStackTrace();
throw new java.lang.Exception(e);
}
}

public String deleteAccount(String acctNo) throws java.lang.Exception{
. . .
}
public String transferMoney(String acctNo, String amount, String direction) throws
java.lang.Exception{
. . .
}
public String listAccount() throws java.lang.Exception{
. . .
}
}

管理コンソールを使用したWebサービス原子性トランザクションの構成

次の項では、WebLogic Server管理コンソールを使用してWebサービス原子性トランザクションを構成する方法について説明します。

- コーディネータと参加者の間で交換されるメッセージの保護

- Webサービス原子性トランザクションの有効化および構成

コーディネータと参加者の間で交換されるメッセージの保護

トランスポート・レベルのセキュリティを使用して、Webサービス原子性トランザクションのコーディネータと参加者の間で交換されるメッセージを保護するには、WebLogic Server管理コンソールで、次の表に定義されているプロパティを構成します。これらのプロパティは、ドメイン・レベルで構成します。詳しい手順は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービス原子性トランザクションの構成に関する項を参照してください。

表15-5 Webサービス原子性トランザクションの保護

プロパティ

説明

Webサービス・トランザクションのトランスポート・セキュリティ・モード

コーディネータと参加者の間のメッセージ交換に双方向SSLを使用するかどうかを指定します。このプロパティは、次のいずれかの値に設定できます。

- SSLは不要: Webサービス・トランザクションのプロトコル・メッセージはすべて、HTTPチャネル経由で交換されます。

- SSLが必要: Webサービス・トランザクションのプロトコル・メッセージはすべて、HTTPSチャネル経由で交換されます。このフラグは、原子性トランザクションが有効になっているMicrosoft .NET Webサービスを起動する際に有効にする必要があります。

- クライアント証明書が必要: Webサービス・トランザクションのプロトコル・メッセージはすべてHTTPS経由で交換され、クライアント証明書が必要となります。

詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプの双方向SSLの構成に関する項を参照してください。

Webサービス・トランザクションの発行済みトークンを有効化

発行済トークンを使用してコーディネータと参加者の間の認証を有効にするかどうかを指定するフラグ。

IssuedTokenは、コーディネータによって発行され、セキュリティ・コンテキスト・トークン(SCT)と署名用のセッション・キーで構成されます。参加者は、共有セッション・キーを使用して署名した署名を登録メッセージに入れて送信します。コーディネータは、セッション・キーを使用して署名を検証することにより、参加者を認証します。

Webサービス原子性トランザクションの有効化および構成

Webサービス原子性トランザクションを有効にしてバージョンとフロー・タイプを構成する場合、Webサービスまたはクライアントのエンドポイント・レベルまたはメソッド・レベルで構成をカスタマイズできます。詳しい手順は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービス原子性トランザクションの構成に関する項を参照してください。

クラスタ環境でのWebサービス原子性トランザクションの使用

原子性トランザクションに対応しているWebサービスをクラスタ環境で使用する際の考慮事項については、第23章「クラスタ内のWebサービスの管理」を参照してください。

Webサービス原子性トランザクションのその他の使用例

Webサービス原子性トランザクションのその他の使用例については、次の項を参照してください。

- Webサービス原子性トランザクションで交換されるメッセージ・ヘッダーの署名と暗号化の方法を示す例は、『Oracle WebLogic Server WebLogic Webサービスの保護』のWebサービス原子性トランザクションの保護に関する項を参照してください。

注意:
Webサービス原子性トランザクションが有効なアプリケーションを保護するために使用できるのは、WebLogic Webサービスのセキュリティ・ポリシーのみです。Oracle Web Services Manager (WSM)ポリシーを使用して保護することはできません。

- Webサービス原子性トランザクションの詳しい例がWebLogic Serverサンプル・アプリケーションの一部として提供されています。サンプル・アプリケーションの実行と例へのアクセスの詳細は、Oracle WebLogic Serverの理解のサンプル・アプリケーションおよびサンプル・コードに関する項を参照してください。

16 Fast Infosetを使用したXML転送の最適化

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic WebサービスにFast Infosetを使用する方法について説明します。

この章の内容は次のとおりです:

- Fast Infosetの概要

- WebサービスでのFast Infosetの有効化

- Webサービス・クライアントでのFast Infosetの有効化および構成

- WebサービスおよびクライアントでのFast Infosetの無効化

Fast Infosetの概要

Fast Infosetは圧縮されたバイナリ・エンコーディング・フォーマットで、テキストベースのXMLフォーマットより効率的にシリアライズできます。Fast Infosetでは、ドキュメント・サイズと処理パフォーマンスの両方が最適化されます。

Fast Infosetが有効な場合、データが送信される前に、SOAPエンベロープ内のXML情報セットは、圧縮されたバイナリ・フォーマットに変換されます。Fast Infosetでは、暗号化メッセージ、署名されたメッセージ、MTOM対応メッセージおよびSOAP添付ファイルが最適化され、HTTPとJMSの両方のトランスポートがサポートされます。

Fast Infosetの仕様、ITU-T Rec.X.891 and ISO/IEC 24824-1 (Fast Infoset)は、ITU-TとISOの両方の標準化団体で定義されています。この仕様は、ITU Webサイト、http://www.itu.int/rec/T-REC-X.891-200505-I/enからダウンロードできます。

Fast Infoset機能は、すべてのWebサービスにおいて、デフォルトで有効です。Webサービス・クライアントの場合、Fast Infosetは、Webサービスで有効化されWSDLで通知されている場合にのみ有効となります。

Fast Infosetは、Webサービスまたはクライアントで、明示的に有効化および構成できます。これについて、次の項で説明します。

WebサービスでのFast Infosetの有効化

Fast Infoset機能は、デフォルトで、Webサービスで有効化され、WSDLに通知されています。次のいずれかの方法を使用することにより、WebサービスでFast Infosetを明示的に有効にできます。

- 設計時にcom.oracle.webservices.api.FastInfosetServiceアノテーションを使用する(「設計時に@FastInfosetServiceアノテーションを使用する例」を参照)。アノテーションの詳細は、『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』の@FastInfosetServiceに関する項を参照してください。

- デプロイメント後にoracle/fast_infoset_service_policyをWebサービスにアタッチする。詳細は、次の項を参照してください。

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のFusion Middleware Controlを使用したWebサービスおよびクライアントへのポリシーのアタッチに関する項

- 『Webサービスの管理』のWLSTを使用したFast Infosetの構成に関する項

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のoracle/fast_infoset_service_policyに関する項

設計時に@FastInfosetServiceアノテーションを使用する例

次のコードの抜粋は、com.oracle.webservices.api.FastInfosetServiceアノテーションを使用して、設計時にWebサービスでFast Infosetを有効化および構成する例です。

package examples.webservices.hello_world;
import javax.jws.WebService;
import com.oracle.webservices.api.FastInfosetService;

@WebService(name="HelloWorldPortType", serviceName="HelloWorldService")
@FastInfosetService(enabled=true)

public class HelloWorldImpl {
public String sayHelloWorld(String message) {
try {
System.out.println("sayHelloWorld:" + message);
} catch (Exception ex) { ex.printStackTrace(); }
return "Message from FI Enabled Service: '" + message + "'";
}
}

Webサービス・クライアントでのFast Infosetの有効化および構成

次のいずれかの方法を使用することにより、Webサービス・クライアントでFast Infosetを明示的に有効化および構成できます。

- 設計時にcom.oracle.webservices.api.FastInfosetClientFeature機能クラスを使用する(「設計時にFastInfosetClientFeature機能クラスを使用する例」を参照)。

- デプロイメント後にoracle/fast_infoset_client_policyをWebサービスにアタッチする。詳細は、次の項を参照してください。

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のFusion Middleware Controlを使用したWebサービスおよびクライアントへのポリシーのアタッチに関する項

- 『Webサービスの管理』のWLSTを使用したFast Infosetの構成に関する項

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のoracle/fast_infoset_client_policyに関する項

コンテンツ・ネゴシエーション戦略の構成

Fast Infosetがクライアントで有効な場合は、コンテンツ・ネゴシエーション・ポリシーの構成が可能です。表16-1で、com.oracle.webservices.api.FastInfosetContentNegotiationTypeによって定義される有効なコンテンツ・ネゴシエーション戦略について説明します。

表16-1 コンテンツ・ネゴシエーション戦略

値

説明

OPTIMISTIC

Fast Infosetがサービスで有効と見なします。すべてのリクエストがFast Infosetを使用して送信されます。

PESSIMISTIC

クライアントからの最初のリクエストは、Fast Infosetを有効にするのではなく、クライアントでFast Infoset機能がサポートされていることを示すHTTP受入れヘッダーを使用して送信されます。サービス・レスポンスがFast Infosetフォーマットで、サービスでFast Infosetが有効であることが確認されると、クライアントからの後続のリクエストはFast Infosetフォーマットで送信されます。

NONE

クライアント・リクエストではFast Infosetは使用されません。

次の点に注意してください。

- コンテンツ・ネゴシエーション戦略がクライアントで明示的に構成されている場合:

- WSDLで通知されているネゴシエーション戦略より優先されます。

- 構成されているコンテンツ・ネゴシエーション戦略が、サービスにより通知されている機能と競合する場合(クライアントでOPTIMISTICが構成され、サービスでFast Infosetが無効にされている場合など)は、例外が生成されます。

- コンテンツ・ネゴシエーション戦略がクライアントで明示的に構成されていない場合:

- Fast Infosetがサービスで有効化および通知されている場合、OPTIMISTICコンテンツ・ネゴシエーション戦略が使用されます。

- Fast Infosetがサービスで無効化され、通知されていない場合、NONEコンテンツ・ネゴシエーション戦略が使用されます。

設計時にFastInfosetClientFeature機能クラスを使用する例

次のコードの抜粋は、com.oracle.webservices.api.FastInfosetClientFeature機能クラスを使用して、設計時にWebサービスでFast Infosetを有効化および構成する例です。

package examples.webservices.hello_world.client;

import javax.xml.namespace.QName;
import java.net.MalformedURLException;
import java.net.URL;
import com.oracle.webservices.api.FastInfosetClientFeature;
import com.oracle.webservices.api.FastInfosetContentNegotiationType;

public class Main {

public static void main(String[] args) {
HelloWorldService service;
FastInfosetContentNegotiationType clientNeg  =
FastInfosetContentNegotiationType.PESSIMISTIC;
FastInfosetClientFeature feature =
FastInfosetClientFeature.builder().fastInfosetContentNegotiation(clientNeg).enabled(true).build();
try {
service = new HelloWorldService(new URL(args[0] + "?WSDL"), new QName("http://hello_world.webservices.examples/", "HelloWorldService") );
} catch (MalformedURLException murl) { throw new RuntimeException(murl); }
HelloWorldPortType port = service.getHelloWorldPortTypePort(feature);

String result = null;
result = port.sayHelloWorld("Hi there!");
System.out.println( "Got result: " + result );
}
}

WebサービスおよびクライアントでのFast Infosetの無効化

設計時にFast Infosetを明示的に無効にするには次のようにします。

- Webサービスの場合、アノテーションでenabledフラグをfalseに設定する(「WebサービスでのFast Infosetの有効化」を参照)。

- Webサービス・クライアントの場合、アノテーションまたは機能クラスでenabledフラグをfalseに設定するか、コンテンツ・ネゴシエーション戦略をNONEに設定する(「Webサービス・クライアントでのFast Infosetの有効化および構成」を参照)。

次のコードの抜粋は、com.oracle.webservices.api.FastInfosetServiceアノテーションを使用して、設計時にWebサービスでFast Infosetを無効化する例です。

package examples.webservices.hello_world;
import javax.jws.WebService;
import com.oracle.webservices.api.FastInfosetService;

@WebService(name="HelloWorldPortType", serviceName="HelloWorldService")
@FastInfosetService(enabled=false)

public class HelloWorldImpl {
public String sayHelloWorld(String message) {
try {
System.out.println("sayHelloWorld:" + message);
} catch (Exception ex) { ex.printStackTrace(); }
return "Message from FI Enabled Service: '" + message + "'";
}
}

デプロイメント後にFast Infosetを無効にするには次のようにします。

- Webサービスまたはクライアントから、それぞれoracle/fast_infoset_service_policyポリシー、oracle/fast_infoset_client_policyポリシーをデタッチする。
詳細は、次の項を参照してください。

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のFusion Middleware Controlを使用したWebサービスおよびクライアントへのポリシーのアタッチに関する項

- 『Webサービスの管理』のWLSTを使用したFast Infosetの構成に関する項

- グローバルにFast Infosetを無効にする場合は、Webサービスまたはクライアントの上位スコープで、それぞれoracle/no_fast_infoset_service_policyポリシー、oracle/no_fast_infoset_client_policyポリシーを含むポリシー・セットを定義する。
詳細は、次の項を参照してください。

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のポリシー・セットを使用したグローバルなポリシーのアタッチに関する項

- 『Oracle Web Services ManagerによるWebサービスの保護とポリシーの管理』のWLSTによるポリシー・セットを使用したグローバルなポリシーのアタッチに関する項

17 SOAP Over JMSトランスポートの使用

この章では、Java API for XML Web Services (JAX-WS)を使用するWebLogic Server 12.1.3用のWebLogic Webサービスの接続プロトコルとして、SOAP over Java Messaging Service (JMS)トランスポートを使用する方法について説明します。

注意:
SOAP over JMSトランスポートは、Webサービス機能のうち、信頼性のあるメッセージングおよびHTTPトランスポート固有のセキュリティとは互換性がありません。

この章の内容は次のとおりです:

- SOAP Over JMSトランスポートの概要

- JMSトランスポート用のWebLogic Serverドメインの構成

- JMSトランスポートを使用したWebサービスの開発: Javaからの開始

- JMSトランスポートを使用したWebサービスの開発: WSDLからの開始

- JMSトランスポートを使用したWebLogic Webサービスの呼出し

- JMSトランスポート・プロパティの構成

- SOAP Over JMSトランスポートの監視

SOAP Over JMSトランスポートの概要

通常、Webサービスおよびクライアントは、接続プロトコルとしてSOAP over HTTP/Sを使用して通信します。ただし、クライアント・アプリケーションがトランスポートとしてJMSを使用するようにWebLogic Webサービスを構成することもできます。

SOAP over JMSトランスポートを使用すると、WebサービスとクライアントがHTTP接続ではなくJMS宛先を使用して通信するようになるため、次のような利点があります。

- 信頼性

- スケーラビリティ

- サービス品質

Webサービスの信頼性のあるメッセージングの場合と同様に、メソッド呼出しがまだキューに入っているときにWebLogic Serverが停止しても、再起動すればすぐに処理が行われます。クライアントは、Webサービスを呼び出す際にレスポンスを待機しないため、クライアントの実行は続行可能です。ただし、SOAP over JMSトランスポートを使用する場合は、HTTP/Sより若干オーバーヘッドが大きくなり、プログラムが複雑になります。

指定する各トランスポートに対し、WebLogic ServerはWSDL内に追加のポートを生成します。このため、Webサービス呼出し時に使用できるトランスポート(JMS、HTTPまたはHTTPS)をクライアント・アプリケーションで選択できるようにするには、明示的に各トランスポートを構成する必要があります。トランスポートは、JWSアノテーションか、jwsc Antタスクの子要素を使用して構成します。

JMSトランスポートのみを構成する場合、HTTPを使用してWebサービスを呼び出すことはできませんが、HTTPを使用してそのWebサービスのWSDLを参照できます。これにより、clientgenはやはりWebサービスのJAX-WSスタブを生成できます。

注意:
JMSトランスポートの使用は、WebLogicの特徴です。.NETクライアントなど、WebLogic以外のクライアント・アプリケーションでは、JMSポートを使用してWebサービスを呼び出すことができない場合があります。

図17-1は、SOAP over JMSトランスポートを使用したWebサービスの呼出しのリクエストおよびレスポンス・メッセージのフローを示しています。

- クライアント・スタブはWebサービスを呼び出し、JMSリクエスト・キュー経由でSOAPリクエスト・メッセージをWebサービスに送信して、レスポンスを待機します。

- サーバー側で、MDBリスナーがリクエストを受け取り、サービス・エンドポイントを呼び出します。

- 処理が行われると、サービス・エンドポイントはレスポンスをJMSレスポンス・キューに送信します。

- クライアント側のJMSリスナーがレスポンスを受け取り、これをクライアントに渡します。

- クライアントがjava.io.Closable.close()コマンドを発行すると、JMSレスポンス・エンドポイントおよびリスナーが削除されます。

図17-1 SOAP Over JMSトランスポートを使用したWebサービスの呼出し

図17-2は、SOAP over JMSトランスポートを使用した非同期Webサービスの呼出しのリクエストおよびレスポンス・メッセージのフローを示しています。

- クライアント・スタブは非同期にWebサービスを呼び出し、JMSリクエスト・キュー経由でSOAPリクエスト・メッセージをWebサービスに送信します。クライアント・スタブはjavax.xml.ws.Responseまたはjava.util.concurrent.Future<T>インスタンスを戻し、レスポンスを待機しません。

- サーバー側で、MDBリスナーがリクエストを受け取り、サービス・エンドポイントを呼び出します。

- 処理が行われると、サービス・エンドポイントはレスポンスをJMSレスポンス・キューに送信します。

- JMSリスナーはレスポンス・エンドポイントを呼び出し、これにより、クライアントのResponseまたはFuture<T>インスタンスが移入されます。

- クライアントがjava.io.Closable.close()コマンドを発行すると、JMSレスポンス・エンドポイントおよびリスナーが削除されます。

図17-2 SOAP Over JMSトランスポートを使用した非同期Webサービスの呼出し

JMS宛先にリクエスト・メッセージを送信する前に、クライアントは表17-1で定義しているJMSメッセージ・プロパティを設定します。

表17-1 リクエスト・メッセージで定義されるJMSメッセージ・プロパティ

JMSメッセージ・プロパティ

説明

SOAPJMS_bindingVersion

SOAP JMSバインディングのバージョン。このリリースでは、この値は1.0に設定する必要があります。

SOAPJMS_contentType

メッセージのMIMEコンテンツ・タイプ。

SOAPJMS_requestURI

JMSリクエストURI。値の構成方法の詳細は、「JMSリクエストURIの構成」を参照してください。

SOAPJMS_soapAction

リクエストの目的を定義するSOAPアクション。

SOAPJMS_targetService

Webサービスのポート・コンポーネント名。

messageType

リクエスト・メッセージで使用するメッセージ・タイプ。BYTESの値は、com.oracle.webservices.api.jms.JMSMessageType.BYTESオブジェクトが使用されることを示します。TEXTの値は、com.oracle.webservices.api.jms.JMSMessageType.TEXTオブジェクトが使用されることを示します。この値のデフォルトはBYTESです。

JMSMessageID

JMSメッセージを一意に識別し、レスポンス・メッセージとリクエストとの相互関連付けに使用されるID。レスポンス・メッセージのJMSCorrelationIDプロパティは、リクエスト・メッセージのJMSMessageIDと一致していることが必要です。

ECIDContext

実行コンテキスト識別子(ECID)、ラッパー・コードおよびエンコーディングの詳細。この内容は、HTTPヘッダーに指定するものと似ており、クライアントのみに必要となります。

JMS宛先にレスポンス・メッセージを送信する前に、サービスは表17-1で定義しているJMSメッセージ・プロパティを設定します。

表17-2 レスポンス・メッセージで定義されるJMSメッセージ・プロパティ

JMSメッセージ・プロパティ

説明

SOAPJMS_bindingVersion

SOAP JMSバインディングのバージョン。このリリースでは、この値は1.0に設定する必要があります。

SOAPJMS_contentType

メッセージのMIMEコンテンツ・タイプ。

JMSCorrelationID

リクエスト・メッセージとレスポンス・メッセージの相互関連付けに使用されるID。JMSCorrelationIDは、リクエスト・メッセージのJMSMessageIDと一致していることが必要です。

JMSMessageID

JMSメッセージを一意に識別し、レスポンス・メッセージとリクエストとの相互関連付けに使用されるID。

JMSトランスポート用のWebLogic Serverドメインの構成

表17-3は、WebLogic ServerドメインでJMSトランスポートによりデフォルトで使用されるリソースを示します。

表17-3 JMSトランスポートにより使用されるデフォルトのリソース

リソース名(デフォルト)

リソース・タイプ

説明

WseeSoapjmsJmsServer

JMSサーバー

JMSサーバー管理コンテナ。

JMSサーバーを手動で構成するには、『Oracle WebLogic Server JMSリソースの管理』のJMS構成に関する項を参照してください。

WseeSoapjmsFileStore

ファイル・ストア

I/O操作を処理し、データを保存したり、物理ストレージ(ファイル、DBMSなど)から取得したりするためにWeb Serverが使用するファイル・ストアまたは物理ストア。

ファイル・ストアを手動で構成する方法は、『Oracle WebLogic Serverサーバー環境の管理』のWebLogic永続ストアの使用に関する項を参照してください。

WseeSoapjmsJmsModule

JMSモジュール

SOAP over JMSトランスポートに必要なJMSリソースを定義するJMSモジュール。

JMSモジュールを手動で構成するには、『Oracle WebLogic Server JMSリソースの管理』のJMS構成に関する項を参照してください。

WseeSoapjmsJmsServerSub

JMSサブデプロイメント

JMSリソースのターゲットをWseeSoapJmsServerに指定するJMSサブデプロイメント。

JMSサブデプロイメントを手動で構成するには、『Oracle WebLogic Server JMSリソースの管理』のJMS構成に関する項を参照してください。

com.oracle.webservices.api.jms.ConnectionFactory

JMS接続ファクトリ

SOAP over JMSトランスポートの接続の作成に使用するデフォルトのJMS接続ファクトリ。

jndiConnectionFactoryName JMSトランスポート・プロパティを使用して別の接続ファクトリを構成することもできます。「JMSトランスポート・プロパティの構成」を参照してください。

com.oracle.webservices.api.jms.RequestQueue

JMSキュー

デフォルトのJMSリクエスト・キュー。

destinationName JMSトランスポート・プロパティを使用して別のJMSリクエスト・キューを構成することもできます。「JMSトランスポート・プロパティの構成」を参照してください。

com.oracle.webservices.api.jms.ResponseQueue

JMSキュー

デフォルトのJMSレスポンス・キュー。

別のJMSレスポンス・キューを構成することもできます。「JMSレスポンス・キューの構成」を参照してください。

ドメインを作成または拡張する際には、WebLogic JAX-WS SOAP/JMS拡張テンプレート(wls_webservice_soapjms.jar)を適用して、JMSトランスポートのサポートに必要なJMSリソースを自動的に構成できます。

JMSトランスポートのサポートに必要なJMSリソースを自動的に構成するには、次のいずれかの方法を使用します。

- 『Oracle Fusion Middleware構成ウィザードによるWebLogicドメインの作成』で説明されているように、構成ウィザードを使用してドメインを作成または拡張します。ドメインを作成または拡張するのに使用するテンプレートの指定を要求されたらWebLogic JAX-WS SOAP/JMS拡張テンプレートを選択します。

- 『WebLogic Scripting Toolの理解』のWebLogicドメインの編集(オフライン)に関する項の説明に従ってWLSTを使用し、wls_webservice_soapjms.jar拡張テンプレートJARファイルによりドメインを拡張します。

この拡張テンプレートの使用は必須ではありませんが、使用すると必要なリソースの構成が格段に容易になります。もう1つの方法として、Oracle WebLogic Server管理コンソールまたはWLSTを使用し、必要なリソースを手動で構成することも可能です。

JMSトランスポートのサポートに必要なリソースを手動で構成するには、次のいずれかの方法を使用します。

- WebLogic Server管理コンソールを使用し、表17-3で説明されているリソースを作成する。詳細は、『Oracle WebLogic Server JMSリソースの管理』のJMS構成に関する項を参照してください。

- WLSTを使用し、表17-3で定義されているリソースを作成する。詳細は、『WebLogic Scripting Toolの理解』の既存のWebLogicドメインの作成に関する項を参照してください。

JMSトランスポートを使用したWebサービスの開発: Javaからの開始

Javaから開始する際にWebサービスにJMSトランスポートを使用するには、次の少なくとも1つのタスクを実行する必要があります。

- JWSファイルに@com.oracle.webservices.api.jms.JMSTransportServiceアノテーションを追加する。

- jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を追加する。この設定は、JWSファイルで定義されたトランスポートをオーバーライドします。

次の手順では、Javaから開始する際に、JMSトランスポートを使用して現在のWebサービスを呼び出すために必要なすべての手順について説明します。

表17-4 JMSトランスポートを使用したWebサービスの開発手順: Javaからの開始

#

手順

説明

1

前提条件を完了します。

Webサービスを実装する基本的なJWSファイルが作成されており、JMSトランスポートを使用して呼び出すWebサービスを構成することが前提となっています。

また、Antベースの開発環境を設定済であり、かつjwsc Antタスクを実行してサービスをデプロイするためのターゲットを含む、作業用のbuild.xmlファイルがあることも前提となっています。

詳細は、第3章「JAX-WS Webサービスの開発」を参照してください。

2

必要なJMSコンポーネント用にWebLogic Serverドメインを構成します。

「JMSトランスポート用のWebLogic Serverドメインの構成」を参照してください。

3

JWSファイルに@com.oracle.webservices.api.jms.JMSTransportServiceアノテーションを追加する。(オプション)

この手順はオプションです。JWSファイルに@JMSTransportServiceアノテーションを追加しない場合、<jmstransportservice>子要素をjwsc Antタスクの<jws>要素に追加する必要があります(手順4を参照)。

「@JMSTransportServiceアノテーションの使用」を参照してください。

4

jwsc Antタスクに<jmstransportservice>子要素を追加します。(オプション)

<jmstransportservice>子要素を使用して、JWSファイルで定義されているトランスポートをオーバーライドします。

この手順は、手順3で@JmsTransportServiceアノテーションをJWSファイルに追加しなかった場合に必要となります。それ以外の場合、この手順は省略可能です。

詳細は、「Ant build.xmlファイルでの<jmstransportservice>子要素の使用」を参照してください。

5

jwscタスクを呼び出すbuild.xml Antファイル内のターゲットを実行することにより、Webサービスをビルドします。

たとえば、jwsc Antタスクを呼び出すターゲットがbuild-serviceというものであれば、以下を実行します。

prompt> ant build-service

「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

6

WebサービスをWebLogic Serverにデプロイします。

「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

JMSトランスポートを使用してWebサービスを呼び出すようにクライアント・アプリケーションを更新する方法については、「JMSトランスポートを使用したWebLogic Webサービスの呼出し」を参照してください。

@JMSTransportServiceアノテーションの使用

JWSファイルをプログラミングする時点で、Webサービスの呼出しにクライアント・アプリケーションで(HTTP/Sではなく) JMSトランスポートを使用することが決まっている場合は、@com.oracle.webservices.api.jms.JMSTransportServiceを使用してその呼出しの詳細を指定できます。

JWSファイルに含めることができる@JMSTransportServiceアノテーションは1つのみです。

必要に応じて、@JMSTransportServiceアノテーションを使用して、宛先名、接続ファクトリ、配信モードなどのJMSトランスポート・プロパティを構成できます。詳細は、「JMSトランスポート・プロパティの構成」を参照してください。

後のビルド時に、"jwsc" jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を指定することにより、JWSファイルで定義されている呼出しをオーバーライドし、JMSトランスポート指定を追加できます。「Ant build.xmlファイルでの<jmstransportservice>子要素の使用」を参照してください。

例17-1は、ステートレスEJBとして実装された、@JMSTransportServiceアノテーションを使用するJWSファイルからの抜粋を示しています。関連するコードについては太字で示されています。

例17-1 @JMSTransportServiceアノテーションを使用したステートレスEJBに対するJMSトランスポートの有効化

package jaxws.ejb;
...
import javax.ejb.Stateless;
import javax.jws.WebService;
import com.oracle.webservices.api.jms.JMSTransportService;

@WebService(name = "Simple", targetNamespace = "http://example.org")
@JMSTransportService(
targetService="SimpleEjbService",
destinationName="com.oracle.webservices.api.jms.RequestQueue",
jndiConnectionFactoryName="weblogic.jms.ConnectionFactory",
mdbPerDestination=false,
activationConfig=("transAttribute=Never;maxBeansInFreePool=1000;
dispatchPolicy=weblogic.wsee.jaxws.mdb.DispatchPolicy"
)
@Stateless
public class SimpleEjb { ... }

例17-2は、@JMSTransportServiceアノテーションを使用するプロバイダベースのWebサービスからの抜粋を示しています。関連するコードについては太字で示されています。

例17-2 @JMSTransportServiceアノテーションを使用したプロバイダベースのWebサービスに対するJMSトランスポートの有効化

package examples.webservices.jaxws;
...
import javax.xml.transform.Source;
import javax.xml.ws.Provider;
import javax.xml.ws.ServiceMode;
import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.Service;
import java.io.ByteArrayInputStream;
import com.oracle.webservices.api.jms.JMSTransportService;

@ServiceMode(value=Service.Mode.PAYLOAD)
@WebServiceProvider(portName="WarehouseServicePort",
serviceName="WarehouseService",targetNamespace="http://examples.org/")
@JMSTransportService(destinationName="myQueue")
public class WarehouseServiceImpl implements Provider<Source> {

public Source invoke(Source source) { ... }
}

Ant build.xmlファイルでの<jmstransportservice>子要素の使用

JMSトランスポートは、jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を追加することにより、ビルド時に指定できます。ビルド時にJMSトランスポートを構成するのは、次のいずれかの場合です。

- @JMSTransportServiceアノテーションを使用してJWSファイルに指定された属性値をオーバーライドする。

- JWSファイルに@JMSTransportServiceアノテーションが含まれず、クライアントがJMSトランスポートを使用してWebサービスを呼び出すようにすることをビルド時に決定する。

jwsc Antタスクの<jmstransportservice>子要素は、JWSファイルの@JMSTransportServiceトランスポート・アノテーションより優先されます。

必要に応じて、<jmstransportservice>要素を使用して、宛先名、宛先タイプ、配信モードなどのJMSトランスポート・プロパティを構成できます。サポートされるJMSトランスポート・プロパティの完全なリストは、「JMSトランスポート・プロパティの構成」を参照してください。

例17-3は、jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を使用して、JMSトランスポートを有効化および構成する方法を示すbuild.xmlファイルからの抜粋を示しています。関連するコードは太字で示されています。

例17-3 <jmstransportservice>子要素を使用したJMSトランスポートの有効化

<?xml version="1.0"?>
<project name="jaxws.jms.jwsc" default="all">
<import file="../build-jms.xml"/>
<path id="client.class.path">
<pathelement path="${clientclasses.dir}"/>
<pathelement path="${java.class.path}"/>
</path>
<target name="jwsc">
<jwsc srcdir="." sourcepath="client" destdir="${output.dir}" debug="on"
keepGenerated="yes">
<jws file="JWSCEndpoint.java" type="JAXWS" explode="true">
<jmstransportservice
targetService="JWSCEndpointService"
destinationName="com.oracle.webservices.api.jms.RequestQueue"
jndiInitialContextFactory="weblogic.jndi.WLInitialContextFactory"
jndiConnectionFactoryName="weblogic.jms.XAConnectionFactory"
jndiURL="t3://localhost:7001"
deliveryMode=com.oracle.webservices.api.jms.JMSDeliveryMode.PERSISTENT
timeToLive=60000
priority=1
messageType=com.oracle.webservices.api.jms.JMSMessageType.BYTES
activationConfig = "transAttribute=Supports"
/>
</jws>
</jwsc>
</target>
</project>

jwsc Antタスクの使用方法の詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のjwscに関する項を参照してください。

JMSトランスポートを使用したWebサービスの開発: WSDLからの開始

WSDLから開始する際にWebサービスにJMSトランスポートを使用するには、次の少なくとも1つのタスクを実行する必要があります。

- wsdlc Antタスクを実行する前に、JMSトランスポートを使用するようにWSDLを更新します。

- @com.oracle.webservices.api.jms.JMSTransportServiceアノテーションを追加するように、wsdlc Antタスクによって生成される途中まで作成済のJWS実装ファイルを更新します。

- JWS実装ファイルの作成に使用されるjwsc Antタスクの<jws>要素に、<jmstransportservice>子要素を追加します。この設定は、JWSファイルで定義されたトランスポートをオーバーライドします。

次の手順では、WSDLから開始する際に、JMSトランスポートを使用して現在のWebサービスを呼び出すために必要なすべての手順について説明します。

表17-5 JMSトランスポートを使用したWebサービスの開発手順: WSDLからの開始

#

手順

説明

1

前提条件を完了します。

この手順では既存のWSDLファイルがあることを前提としています。

2

必要なJMSコンポーネント用にWebLogic Serverドメインを構成します。

「JMSトランスポート用のWebLogic Serverドメインの構成」を参照してください。

3

JMSトランスポートを使用するようWSDLを更新する(オプション)

この手順はオプションです。JMSトランスポートを使用するようWSDLを更新しなかった場合、以下の少なくとも1つの作業を行う必要があります。

- 途中まで作成済のJWSファイルを編集して@JMSTransportServiceアノテーションをJWSファイルに追加します(手順5を参照)。

- jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を追加します(手順7を参照)。

「JMSトランスポートを使用するためのWSDLの更新」を参照してください。

4

WSDLファイルに対してwsdlc Antタスクを実行します。

たとえば、wsdlc Antタスクを呼び出すターゲットがgenerate-from-wsdlというものであれば、以下を実行します。

prompt> ant generate-from-wsdl

「wsdlc WebLogic WebサービスAntタスクの実行」を参照してください。

5

途中まで作成済みのJWSファイルを更新します。

wsdlc Antタスクにより途中まで作成済のJWSファイルが生成されます。必要な動作をWebサービスに実装するには、独自のビジネス・コードをWebサービスに追加する必要があります。「wsdlcで生成される途中まで作成済のJWS実装クラス・ファイルの更新」を参照してください。

手順3で、JMSトランスポートを使用するようにWSDLを更新した場合、JWSファイルには、JMSトランスポートを定義する@JMSTransportServiceアノテーションが含まれます。@JMSTransportServiceアノテーションがJWSファイルに含まれない場合、次の少なくとも1つの作業を行う必要があります。

- JWSファイルを編集して、@JMSTransportServiceアノテーションをJWSファイルに追加します(「@JMSTransportServiceアノテーションの使用」を参照)。

- jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を追加します(手順7を参照)。

6

jwsc Antタスクに<jmstransportservice>子要素を追加します。(オプション)

<jmstransportservice>子要素を使用して、JWSファイルで定義されているトランスポートをオーバーライドします。この手順は、JWSファイルに@JMSTransportServiceアノテーションが含まれない場合には必須です(手順5を参照)。それ以外の場合、この手順は省略可能です。

詳細は、「Ant build.xmlファイルでの<jmstransportservice>子要素の使用」を参照してください。

7

JWSファイルに対してjwsc Antタスクを実行し、Webサービスをビルドします。

wsdlc Antタスクによって生成されたアーティファクトと更新したJWS実装ファイルを指定して、Webサービスを実装するエンタープライズ・アプリケーションを生成します。

「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

8

WebサービスをWebLogic Serverにデプロイします。

「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

JMSトランスポートを使用してWebサービスを呼び出すようにクライアント・アプリケーションを更新する方法については、「JMSトランスポートを使用したWebLogic Webサービスの呼出し」を参照してください。

JMSトランスポートを使用するためのWSDLの更新

JMSトランスポートを使用するようにWSDLを更新するには、JMSトランスポート情報を定義する<wsdl:binding>定義を追加する必要があります。複数のトランスポート・オプションを指定するかどうかにより、次のいずれかの方法で定義を追加できます。

- 既存のHTTP <wsdl:binding>定義を編集する。

- WSDLで複数のトランスポート・オプション(HTTPやJMSトランスポートなど)を指定する場合は、既存のHTTP <wsdl:binding>定義をコピーし、JMSトランスポートを使用するように編集する。

必要に応じて、バインディングまたはJMS URIレベルでJMSトランスポート・プロパティを構成できます。

次の各項では、JMSトランスポートを使用するためにWSDLを更新する方法について説明します。

- WSDLバインディング・レベルでのJMSトランスポートの有効化

- WSDLでのJMSトランスポート・プロパティの構成

- WSDLでのJMSトランスポートの有効化の例

WSDLバインディング・レベルでのJMSトランスポートの有効化

WSDLバインディング・レベルでJMSトランスポートを有効にするには、<wsdl:binding>要素の<soapwsdl:binding>子要素のtransport属性をhttp://www.w3.org/2010/soapjmsに設定します。

必要に応じて、<wsdl:binding>要素定義内にJMSトランスポート・プロパティを構成できます。「WSDLでのJMSトランスポート・プロパティの構成」を参照してください。

例17-4は、JMSトランスポートの<wsdl:binding>要素の例を示します。この例では、HTTPバインディングも定義されます。

例17-4 WSDLバインディング・レベルでのJMSトランスポートの有効化

...
<binding xmlns:soapjms="http://www.w3.org/2010/soapjms/"
name="AddNumbersJMSBinding" type="tns:AddNumbersPortType">
<soap:binding transport="http://www.w3.org/2010/soapjms/" style="document" />
<operation name="addNumbers">
<soap:operation soapAction="" />
<input>
<soap:body use="literal" />
</input>
<output>
<soap:body use="literal" />
</output>
</operation>
</binding>
<binding name="AddNumbersSOAPBinding" type="tns:AddNumbersPortType">
<soap:binding transport="http://schemas.xmlsoap.org/soap/http" style="document" />
...
</binding>
...

WSDLでのJMSトランスポート・プロパティの構成

必要に応じて、次のWSDL要素内に、JMSトランスポート・プロパティのサブセットを構成できます。

- <wsdl:binding>要素: バインディングを使用するすべてのポートに伝播します。

- JMS URI(「JMS URIの構成」を参照)。

具体的には、WSDLで次のJMSトランスポート・プロパティを構成できます。各プロパティの説明は、表17-6「JMSトランスポート構成プロパティの説明」を参照してください。

- deliveryMode

- jndiConnectionFactoryName

- jndiContextParameters

- jndiInitialContextFactory

- jndiURL

- priority

- replyToName

- timeToLive

例17-5は、JMSトランスポート・プロパティが定義されている<wsdl:binding>要素の例を示します。この場合、JMSトランスポート・プロパティは、バインディングを使用するすべてのポートに伝播します。

例17-5 WSDLでのJMSトランスポート・プロパティの構成

...
<binding xmlns:soapjms="http://www.w3.org/2010/soapjms/"
name="AddNumbersBinding" type="tns:AddNumbersPortType">
<soap:binding transport="http://www.w3.org/2010/soapjms/"
style="document" />
<soapjms:jndiInitialContextFactory>
weblogic.jndi.WLInitialContextFactory
</soapjms:jndiInitialContextFactory>
<soapjms:jndiConnectionFactoryName>
weblogic.jms.XAConnectionFactory
</soapjms:jndiConnectionFactoryName>
<soapjms:bindingVersion>1.0</soapjms:bindingVersion>
<soapjms:destinationName>
com.oracle.webservices.api.jms.RequestQueue
</soapjms:destinationName>
<soapjms:targetService>AddNumbersService</soapjms:targetService>
<soapjms:deliveryMode>
com.oracle.webservices.api.jms.JMSDeliveryMode.PERSISTENT
</soapjms:deliveryMode>
<soapjms:priority>0</soapjms:priority>
<soapjms:messageType>
com.oracle.webservices.api.jms.JMSMessageType.BYTES
</soapjms:messageType>
<soapjms:destinationType>
com.oracle.webservices.api.jms.JMSDestinationType.QUEUE
</soapjms:destinationType>
<operation name="addNumbers">
<soap:operation soapAction="" />
<input>
<soap:body use="literal" />
</input>
<output>
<soap:body use="literal" />
</output>
</operation>
</binding>
...

WSDLでのJMSトランスポートの有効化の例

例17-6は、SOAP over JMSトランスポート用に構成されるWSDLの例を示します。

例17-6 WSDLでのJMSトランスポートの有効化

<?xml version="1.0" encoding="UTF-8"?>

<definitions
name="AddNumbers"
targetNamespace="http://example.org"
xmlns:tns="http://example.org"
xmlns="http://schemas.xmlsoap.org/wsdl/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/">
<types>
<xsd:schema
xmlns="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://example.org"
elementFormDefault="qualified">

<complexType name="addNumbersResponse"
<sequence>
<element name="return" type="xsd:int" />
</sequence>
</complexType>
<element name="addNumbersResponse" type="tns:addNumbersResponse"/>

<complexType name="addNumbers">
<sequence>
<element name="arg0" type="xsd:int" />
<element name="arg1" type="xsd:int" />
</sequence>
</complexType>
<element name="addNumbers" type="tns:addNumbers"/>
</xsd:schema>
</types>
<message name="addNumbers">
<part name="parameters" element="tns:addNumbers" />
</message>
<message name="addNumbersResponse">
<part name="result" element="tns:addNumbersResponse" />
</message>
<portType name="AddNumbersPortType">
<operation name="addNumbers">
<input message="tns:addNumbers" />
<output message="tns:addNumbersResponse" />
</operation>
</portType>
<binding xmlns:soapjms="http://www.w3.org/2010/soapjms/" name="AddNumbersBinding"
type="tns:AddNumbersPortType">
<soap:binding transport="http://www.w3.org/2010/soapjms/" style="document" />
<soapjms:jndiInitialContextFactory>weblogic.jndi.WLInitialContextFactory
</soapjms:jndiInitialContextFactory>
<soapjms:jndiConnectionFactoryName>weblogic.jms.XAConnectionFactory
</soapjms:jndiConnectionFactoryName>
<soapjms:bindingVersion>1.0</soapjms:bindingVersion>
<soapjms:destinationName>com.oracle.webservices.api.jms.RequestQueue
</soapjms:destinationName>
<soapjms:targetService>AddNumbersService</soapjms:targetService>
<soapjms:deliveryMode>com.oracle.webservices.api.jms.JMSDeliveryMode.PERSISTENT
</soapjms:deliveryMode>
<soapjms:priority>0</soapjms:priority>
<soapjms:messageType>com.oracle.webservices.api.jms.JMSMessageType.BYTES
</soapjms:messageType>
<soapjms:destinationType>com.oracle.webservices.api.jms.JMSDestinationType.QUEUE
</soapjms:destinationType>
<operation name="addNumbers">
<soap:operation soapAction="" />
<input>
<soap:body use="literal" />
</input>
<output>
<soap:body use="literal" />
</output>
</operation>
</binding>
<service name="AddNumbersService">
<port name="AddNumbersPort" binding="tns:AddNumbersBinding">
<soap:address location="jms:jndi:com.oracle.webservices.api.jms.RequestQueue?targetService=AddNumbersService&amp;jndiInitialContextFactory=weblogic.jndi.WLInitialContextFactory&amp;jndiConnectionFactoryName=weblogic.jms.XAConnectionFactory"/>

</port>
</service>
</definitions>

JMSトランスポートを使用したWebLogic Webサービスの呼出し

HTTPトランスポートを使用して記述したときと同様にして、JMSトランスポートを使用し、Webサービスを呼び出すクライアント・アプリケーションを記述します。JMSトランスポートの場合、クライアントはSOAPリクエスト・メッセージをJMSリクエストの宛先に送信し、JMSレスポンスの宛先からSOAPレスポンス・メッセージを受信します。Webサービスの呼出しの例は、第9章「JAX-WS Webサービス・クライアントの開発例」を参照してください。

次のいずれかの方法を使用して、Webサービス・クライアントでJMSトランスポートを有効にし、必要に応じて構成します。

- clientgen Antタスクの<jmstransportclient>要素を使用して、JMSトランスポートを有効にして自動的にクライアント・アーティファクトを生成します(「Ant build.xmlファイルでの<jmstransportclient>要素の使用」を参照)。

- 次のいずれかの方法を使用して、JMSトランスポートを構成するように、Webサービス・クライアントを更新します。

- @com.oracle.webservices.api.jms.JMSTransportClientアノテーションを追加する(「@JMSTransportClientアノテーションの使用」を参照)。

- com.oracle.webservices.api.jms.JMSTransportClientFeature機能クライアントAPIを追加する(「JMSTransportClientFeatureクライアントAPIの使用」を参照)。

- 同期クライアントのターゲット・エンドポイント・アドレスとしてJMS URIを構成する(「ターゲット・エンドポイント・アドレスとしてのJMS URIの構成」を参照)。

- JMSトランスポートを有効化および構成するように、非同期Webサービス・クライアントを更新します(「AsyncClientTransportFeatureを使用した非同期クライアントの構成」を参照)。

Ant build.xmlファイルでの<jmstransportclient>要素の使用

clientgenツールでは、JMSトランスポート・バインディングを含むWSDLファイルから、JMSトランスポート・クライアント・プロキシが生成されます。clientgenを使用してクライアント・プロキシを生成する際、clientgen Antタスクに<jmstransportclient>要素を追加することにより、JMSトランスポートを有効にできます。

注意:
HTTPを使用してJMSトランスポートで構成されたWebサービスを呼び出すことはできませんが、HTTPを使用してそのWebサービスのWSDLを参照することはできます。これにより、clientgen AntタスクはやはりWebサービスのJAX-WSアーティファクトを作成できます。

必要に応じて、<jmstransportclient>要素を使用して、宛先名、宛先タイプ、配信モード、リクエストおよびレスポンス・キューなどのJMSトランスポート・プロパティを構成できます。サポートされるJMSトランスポート・プロパティの完全なリストは、「JMSトランスポート・プロパティの構成」を参照してください。

例17-7は、clientgen Antタスクの<jmstransportclient>要素を使用して、JMSトランスポートを有効化および構成する方法を示すbuild.xmlファイルからの抜粋を示しています。関連するコードは太字で示されています。

例17-7 Ant build.xmlファイルでの<jmstransportclient>要素の使用

<target name="clientgen">
<clientgen
wsdl="./WarehouseService.wsdl"
destDir="clientclasses"
packageName="client.warehouse"
type="JAXWS">
<jmstransportclient
targetService="JWSCEndpointService"
destinationName="com.oracle.webservices.api.jms.RequestQueue"
jndiInitialContextFactory="weblogic.jndi.WLInitialContextFactory"
jndiConnectionFactoryName="weblogic.jms.ConnectionFactory"
jndiURL="t3://localhost:7001"
timeToLive=60000
priority=1
messageType=com.oracle.webservices.api.jms.JMSMessageType.TEXT
replyToName="com.oracle.webservices.api.jms.ResponseQueue"
/>
</clientgen>

clientgen Antタスクの使用の詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のclientgenに関する項を参照してください。

@JMSTransportClientアノテーションの使用

clientgenを実行してWSDLファイルからWebサービス・クライアント・アーティファクトを生成すると、ビルド・ファイルで<jmstransportclient>を使用してJMSトランスポートが有効化されている場合、生成されたクライアント・プロキシに自動的に@com.oracle.webservices.api.jms.JMSTransportClientアノテーションが含まれます(「Ant build.xmlファイルでの<jmstransportclient>要素の使用」を参照)。

clientgenにより自動的に@JMSTransportClientアノテーションが構成されない場合は、これを手動でファイルに追加できます。

必要に応じて、@JMSTransportClientアノテーションを使用して、次のJMSトランスポート・プロパティを構成できます。各プロパティの説明は、表17-6「JMSトランスポート構成プロパティの説明」を参照してください。

- destinationName

- destinationType

- enabled

- jmsMessageHeader

- jmsMessageProperty

- jndiConnectionFactoryName

- jndiContextParameters

- jndiInitialContextFactory

- jndiURL

- messageType

- priority

- replyToName

- targetService

- timeToLive

例17-8は、@JMSTransportClientアノテーションを使用するクライアント・ファイルからの抜粋を示しています。関連するコードについては太字で示されています。

例17-8 @JMSTransportClientアノテーションを使用したクライアント・プロキシに対するJMSトランスポートの有効化

...
import javax.xml.ws.WebServiceClient;
import com.oracle.webservices.api.jms.JMSTransportClient;
...
@WebServiceClient(name = "WarehouseService", targetNamespace = "http://oracle.com/samples/",
wsdlLocation="WarehouseService.wsdl")
@JMSTransportClient (
destinationName="myQueue",
replyToName="myReplyToQueue",
jndiURL="t3://localhost:7001",
jndiInitialContextFactory="weblogic.jndi.WLInitialContextFactory" ,
jndiConnectionFactoryName="weblogic.jms.ConnectionFactory" ,
timeToLive=1000, priority=1,
messageType=com.oracle.webservices.api.jms.JMSMessageType.TEXT
)

public class WarehouseService  extends Service { ... }

JMSTransportClientFeatureクライアントAPIの使用

com.oracle.webservices.api.jms.JMSTransportClientFeatureクライアントAPIを使用して、Webサービス・クライアントでJMSトランスポートを構成できます。

必要に応じて、com.oracle.webservices.api.jms.JMSTransportClientFeatureを使用して、次のJMSトランスポート・プロパティを構成できます。各プロパティの説明は、表17-6「JMSトランスポート構成プロパティの説明」を参照してください。

- destinationName

- destinationType

- enabled

- jmsMessageHeader

- jmsMessageProperty

- jndiConnectionFactoryName

- jndiContextParameters

- jndiInitialContextFactory

- jndiURL

- messageType

- priority

- replyToName

- targetService

- timeToLive

例17-9は、JMSTransportClientFeatureを使用するWebクライアントからの抜粋を示しています。関連するコードについては太字で示されています。

例17-9 JMSTransportClientFeatureを使用したクライアント・プロキシに対するJMSトランスポートの有効化

...
import javax.xml.namespace.QName;
import java.net.URL;
import com.oracle.webservices.api.jms.JMSTransportClientFeature;
...
URL url = new URL("http://localhost:7001/WarehouseServicePort/WarehouseService?WSDL");
QName serviceName = new QName("http://www.oracle.com/samples/", "WarehouseService");
WarehouseService service = new WarehouseService (url, serviceName);
JMSTransportClientFeature feature =
JMSTransportClientFeature.builder().jndiInitialContextFactory("weblogic.jndi.WLInitialContextFactory").jndiURL("t3://localhost:7001").build();
port = service.getWarehouseShipmentsPort(new WebServiceFeature[]{feature});
Item item = new Item();
item.setProductNumber(10001);
item.setQuantity(100);
port.shipGoods(item, "BEA");
...

例17-10は、JMSTransportClientFeatureを使用するディスパッチ・クライアントからの抜粋を示しています。関連するコードについては太字で示されています。

例17-10 JMSTransportClientFeatureを使用したディスパッチ・クライアントに対するJMSトランスポートの有効化

...
import javax.xml.namespace.QName;
import java.net.URL;
import javax.xml.bind.JAXBContext;
import javax.xml.ws.ServiceMode;
import javax.xml.ws.Dispatch;
import com.oracle.webservices.api.jms.JMSTransportClientFeature;
...
Service service = Service.create(new URL(wsdl), new QName(nameSpace, serviceName));
JAXBContext jaxbContext = JAXBContext.newInstance(ObjectFactory.class);
JMSTransportClientFeature feature =
JMSTransportClientFeature.builder().jndiURL("t3://adc2170585:7003").build();
Dispatch dispatch =
service.createDispatch(new QName(nameSpace, "WarehouseServicePort"), jaxbContext,
Service.Mode.PAYLOAD, new WebServiceFeature[]{feature});
...

ターゲット・エンドポイント・アドレスとしてのJMS URIの構成

クライアント・バインディングのターゲット・エンドポイント・アドレスとしてJMS URIを指定して、Webサービス・クライアントでJMSトランスポートを有効化および構成できます。JMS URIの構築については、「JMS URIの構成」を参照してください。

例17-11は、ターゲット・エンドポイント・アドレスをJMS URIに設定するWebクライアントからの抜粋を示しています。関連するコードについては太字で示されています。この例で、JMSTransportClientFeatureを使用してreplyToNameが構成されている場合、これがターゲット・エンドポイント・アドレス値より優先されます。

例17-11 JMS URIを使用したクライアント・プロキシに対するJMSトランスポートの有効化

...
import javax.xml.namespace.QName;
import java.net.URL;
import javax.xml.ws.BindingProvider;
import javax.xml.ws.handler.MessageContext;
import com.oracle.webservices.api.jms.JMSTransportClientFeature;
...
URL url = new URL("http://localhost:7001/WarehouseServicePort/WarehouseService?WSDL");
QName serviceName = new QName("http://www.oracle.com/samples/", "WarehouseService");
WarehouseService service = new WarehouseService (url, serviceName);
JMSTransportClientFeature feature = new JMSTransportClientFeature().build();
feature.setJndiInitialContextFactory ("weblogic.jndi.WLInitialContextFactory");
feature.setJndiUrl("t3://localhost:7001");
port = service.getWarehouseShipmentsPort(new WebServiceFeature[]{feature});
BindingProvider bp = (BindingProvider) port;
bp.getRequestContext().put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"jms:jndi:myQueue?targetService=WarehouseService&replyToName=myReplyToQueue");
Item item = new Item();
item.setProductNumber(10001);
item.setQuantity(100);
port.shipGoods(item, "BEA");
...

例17-12は、JMSTransportClientFeatureを使用するディスパッチ・クライアントからの抜粋を示しています。関連するコードについては太字で示されています。この例で、JMSTransportClientFeatureで指定されたJMSトランスポート・プロパティは、JMS URIより優先されます。

例17-12 JMS URIを使用したディスパッチ・クライアントに対するJMSトランスポートの有効化の例

...
String uri = "jms:jndi:myQueue?targetService=WarehouseService&jndiConnectionFactoryName=weblogic.jms.ConnectionFactory&jndiURL=t3://adc2170585:7003&jndiInitialContextFactory=weblogic.jndi.WLInitialContextFactory";
Service service = Service.create(new URL(wsdl), new QName(nameSpace, serviceName));
JAXBContext jaxbContext = JAXBContext.newInstance(ObjectFactory.class);
JMSTransportClientFeature feature = new JMSTransportClientFeature().build();
feature.setJndiUrl("t3://adc2170585:7003");

Dispatch dispatch =
service.createDispatch(new QName(nameSpace, "WarehouseServicePort"), jaxbContext,
Service.Mode.PAYLOAD, new WebServiceFeature[]{feature});

dispatch.getRequestContext().put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY, uri );
...

AsyncClientTransportFeatureを使用した非同期クライアントの構成

非同期クライアント・トランスポート機能(「スケーラブルな非同期JAX-WSクライアントの開発(非同期クライアント・トランスポート)」を参照)は、スケーラブルな非同期クライアントのプログラミング・モデルを提供します。

非同期クライアントに対してSOAP over JMSトランスポートを有効にするには:

1. クライアント・バインディングのターゲット・エンドポイント・アドレスとしてJMS URIを指定します。JMS URIの構築については、「JMS URIの構成」を参照してください。

注意:
JMSトランスポートを使用している場合、非同期レスポンス・エンドポイントのコンテキスト・パスがAsyncClientTransportFeatureを使用して指定されていると、これが無視されます。

2. 必要に応じて、AsyncClientTransportFeatureを使用し、addressまたはReplyToヘッダーを構成することにより、永続的なレスポンス・キューを構成します(「非同期クライアント・トランスポート機能の有効化と構成」を参照)。
JMSレスポンス・キューのアドレスを構成しない場合、またはdestinationNameプロパティが匿名に設定されている場合(JMSトランスポートでは、これはサポートされていません)は、一時レスポンス・キューが使用されます。JMSレスポンス・キューの構成の詳細は、「JMSレスポンス・キューの構成」を参照してください。

エンドポイントが呼び出されると、クライアント実行時環境では、レスポンス・エンドポイントが公開され、レスポンスJMSキューにJMSリスナーがデプロイされます。クライアントにアタッチされると、AsyncClientTransportFeatureインスタンスはすべてのクライアント呼出しのレスポンス・エンドポイントを決定します。ターゲットのエンドポイント・アドレス内のreplyToNameプロパティおよびJMSTransportClientFeatureは無視されます。

例17-13は、AsyncClientTransportFeatureを使用する非同期クライアントからの抜粋を示しています。関連するコードについては太字で示されています。この例では、replyToおよびfaultToアドレスが定義され、クライアントに渡されます。

例17-13 非同期クライアントに対するJMSトランスポートの有効化と永続キューの構成の例

...
WarehouseService service = new WarehouseService(url, serviceName);
AsyncClientTransportFeature replyTo = new AsyncClientTransportFeature (
"jms:jndi:myReplyToQueue?targetService=WarehouseService");
AsyncClientTransportFeature faultTo = new AsyncClientTransportFeature (
"jms:jndi:myFaultToQueue?targetService=WarehouseService");
AsyncClientTransportFeature callbackFeature =  new AsyncClientTransportFeature (
replyTo.getEndpointReference(W3CEndpointReference.class),
faultTo.getEndpointReference(W3CEndpointReference.class));
port = service.getWarehouseServicePort(new WebServiceFeature[] { callbackFeature });
status = port.shipGoods(item, "BEAN");
(BindingProvider) port.getRequestContext().put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY,
"jms:jndi:myQueue?targetService=WarehouseService");
((Closable)port).close();
...

JMSトランスポート・プロパティの構成

JMSトランスポートを有効にする際、必要に応じて、JMSトランスポート・プロパティを構成できます。次の各項を参照してください。

- JMSトランスポート構成プロパティの説明

- 構成メソッドと優先順位

- 管理コンソールを使用したJMSトランスポートの構成

- WLSTを使用したJMSトランスポートの構成

- JMS URIの構成

- JMSリクエストURIの構成

- WS-Addressingヘッダーの構成

- JMSレスポンス・キューの構成

- JMSメッセージ・タイプの構成

- WSDLファイルへのHTTPアクセスの構成

JMSトランスポート構成プロパティの説明

表17-6は、構成可能なJMSトランスポート・プロパティと、表17-7で定義したサポートされる構成方法を示しています。

表17-6 JMSトランスポート構成プロパティの説明

名前

説明

サポートされる構成方法

activationConfig

JMSプロバイダに渡されるアクティブ化構成プロパティ。各プロパティは、"name1=value1;...;nameN=valueN"のフォーマットを使用して、名前と値のペアとして指定されます。

例: "key1=value1;key2=value2"

このプロパティでサポートされるアクティブ化構成プロパティのリストは、表17-7を参照してください。

デフォルト値は""です。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

bindingVersion

SOAP JMSバインディングのバージョン。このリリースでは、この値は1.0に設定する必要があります。この値は、com.oracle.webservices.api.jms.JMSBindingVersion.SOAP_JMS_1_0と同等です。

この値は、SOAPJMS_bindingVersion JMSメッセージ・プロパティにマップされます(表17-1を参照)。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

deliveryMode

リクエスト・メッセージが永続的かどうかを示す配信モード。有効な値は、com.oracle.webservices.api.jms.JMSDeliveryMode.PERSISTENTおよびcom.oracle.webservices.api.jms.JMSDeliveryMode.NON_PERSISTENTです。

デフォルト値はcom.oracle.webservices.api.jms.JMSDeliveryMode.PERSISTENTです。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

destinationName

宛先キューまたはトピックのJNDI名。

デフォルト値は"com.oracle.webservices.api.jms.RequestQueue"です。

表17-8内のすべての構成方法

destinationType

宛先タイプ。有効な値は、com.oracle.webservices.api.jms.JMSDestinationType.QUEUEまたはcom.oracle.webservices.api.jms.JMSDestinationType.TOPICです。

デフォルト値はcom.oracle.webservices.api.jms.JMSDestinationType.QUEUEです。

この値は、該当する場合、activationConfigプロパティのエントリとして指定されたdestinationType値(表17-7を参照)をオーバーライドします。

トピックは、一方向通信でのみサポートされます。

表17-8内のすべての構成方法

enabled

JMSトランスポートが有効かどうかを指定するBooleanフラグ。この値のデフォルトはtrueです。

@JMSTransportServiceおよび@JMSTransportClientアノテーション

enableHttpWsdlAccess

HTTPによりWSDLを公開するかどうかを指定するBooleanフラグ。このフラグのデフォルトはtrueです。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

jmsMessageHeader

JMSヘッダー・プロパティ。各プロパティは、"name1=value1&...&nameN=valueN"のフォーマットを使用して、名前と値のペアとして指定されます。

例: "JMSType=car&JMSPriority=4"

デフォルト値は""です。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

- @JMSTransportClientアノテーション

jmsMessageProperty

JMSメッセージ・プロパティ。各プロパティは、"name1=value1&...&nameN=valueN"のフォーマットを使用して、名前と値のペアとして指定されます。

例: "JMSType=car&JMSPriority=4"

デフォルト値は""です。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

- @JMSTransportClientアノテーション

jndiConnectionFactoryName

JMS接続の確立に使用される接続ファクトリのJNDI名。

デフォルト値は"com.oracle.webservices.api.jms.ConnectionFactory"です。

表17-8内のすべての構成方法

jndiContextParameter

JNDIプロパティ。各プロパティは、"name1=value1&...&nameN=valueN"のフォーマットを使用して、名前と値のペアとして指定されます。

JNDIプロバイダのInitialContextコンストラクタに送信されるjava.util.Hashtableにプロパティが追加されます。

デフォルト値は""です。

表17-8内のすべての構成方法

jndiInitialContextFactory

JNDIルックアップに使用される最初のコンテキスト・ファクトリ・クラス名。この値は、java.naming.factory.initialプロパティにマップされます。

デフォルト値は"weblogic.jndi.WLInitialContextFactory"です。

表17-8内のすべての構成方法

jndiURL

JNDIプロバイダのURL。

デフォルト値は"t3://localhost:7001"です。

この値は、java.naming.provider.urlプロパティにマップされます。

表17-8内のすべての構成方法

lookupVariant

指定された宛先名の参照に使用されるメソッド。JMSトランスポートをサポートするには、この値をjndi(デフォルト値)に設定する必要があります。

なし(変更できません)

mdbPerDestination

リクエストされた宛先ごとに1つのリスニング・メッセージドリブンBean (MDB)を作成するかどうかを指定するBooleanフラグ。この値のデフォルトはtrueです。

falseに設定すると、Webサービス・ポートごとに1つのリスニングMDBが作成され、そのMDBは他のポートによって共有できません。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

messageType

リクエスト・メッセージで使用するメッセージ・タイプ。有効な値は、com.oracle.webservices.api.jms.JMSMessageType.BYTESおよびcom.oracle.webservices.api.jms.JMSMessageType.TEXTです。

デフォルト値はcom.oracle.webservices.api.jms.JMSMessageType.BYTESです。

メッセージ・タイプの構成の詳細は、「JMSメッセージ・タイプの構成」を参照してください。

表17-8内のすべての構成方法

priority

リクエストおよびレスポンス・メッセージに関連付けられたJMS優先度。この値は、0 (最低優先度)から9 (最高優先度)までの正の整数で指定します。デフォルト値は0です。

表17-8内のすべての構成方法

replyToName

レスポンス・メッセージが送信されるJMS宛先のJNDI名。

双方向動作の場合、デフォルトで一時レスポンス・キューが生成されます。デフォルトの一時レスポンス・キューを使用することで、必要となる構成が最小限に抑えられます。ただし、サーバーの障害時には、レスポンス・メッセージが失われる可能性があります。

このプロパティにより、クライアントは、応答の受取りにデフォルトの一時キューまたはトピックを使用するのではなく、事前に定義された永続キューまたはトピックを使用できます。JMSレスポンス・キューの構成の詳細は、「JMSレスポンス・キューの構成」を参照してください。

この値は、リクエスト・メッセージのJMSReplyTo JMSヘッダーにマップされます。

デフォルト値は""です。

表17-8内のすべての構成方法

runAsPrincipal

リスニングMDBの実行に使用されるプリンシパル。

デフォルト値は""です。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

runAsRole

リスニングMDBの実行に使用されるロール。

デフォルト値は""です。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

targetService

Webサービスのポート・コンポーネント名。この値は、サービス実装により、サービス・リクエストのディスパッチに使用されます。指定されない場合、WSDLまたは@javax.jws.WebServiceアノテーションのサービス名が使用されます。

この値は、SOAPJMS_targetService JMSメッセージ・プロパティにマップされます。

デフォルト値は""です。

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

- @JMSTransportClientアノテーション

timeToLive

リクエスト・メッセージの存続期間(ミリ秒単位)。0の値は、存続期間が無限であることを示します。指定されない場合、JMSで定義されているデフォルト値、180000Lが使用されます。

サービス側では、timeToLiveでも各MDBトランザクションの期限が指定されます。

表17-8内のすべての構成方法

次の表は、表17-6のactivationConfigプロパティでサポートされるアクティブ化プロパティを示しています。アクティブ化プロパティを使用したMDBの調整については、『Oracle WebLogic Serverのパフォーマンスのチューニング』のメッセージドリブンBeanの調整に関する項を参照してください。

表17-7 activationConfigプロパティでサポートされるアクティブ化プロパティ

名前

説明

acknowledgeMode

メッセージが受信および処理されたことをJMSプロバイダに通知する方法を制御する確認応答モード。有効な値は次のとおりです。

- AUTO_ACKNOWLEDGE: メッセージはただちに確認されます。これがデフォルトです。

- DUPS_OK_ACKNOWLEDGE: 確認応答は遅延し、重複メッセージが受信される可能性があります。

コンテナ管理トランザクションを使用する場合は、確認応答モードは無視されます。(この場合、確認応答はトランザクションのコンテキスト内で実行されます。)

connectionFactoryJndiName

キューおよびトピックの作成にMDBが使用するJMS接続ファクトリのJNDI名。この値のデフォルトはweblogic.jms.MessageDrivenBeanConnectionFactoryです。

destinationJndiName

WebLogic Server JNDIツリーにデプロイされている実際のJMSキューまたはトピックにMDBを関連付けるために使用するJNDI名。

destinationType

JMS宛先のタイプ。有効な値は、QUEUEおよびTOPICです。

dispatchPolicy

MDBのワーク・マネージャ。この値のデフォルトはweblogic.wsee.jaxws.mdb.DispatchPolicyです。

distributedDestinationConnection

同一クラスタ内のWebLogic JMS分散宛先(トピックまたはキュー)にアクセスするMDBが、すべての分散宛先メンバーから消費するか、または現在のWebLogic Serverインスタンスのローカル分散宛先メンバーのみから消費するかを指定する接続設定。有効な値は次のとおりです。

- LocalOnly: MDBは、現在のWebLogic Serverインスタンスのローカル・メンバーからJMS分散宛先を消費します。これがデフォルトです。

- EveryMember: MDBは、すべての分散宛先メンバーからJMS分散宛先を消費します。

durableSubscriptionDeletion

MDBがアンデプロイまたは削除されるときに恒久トピック・サブスクリプションが自動的に削除されるようにするかどうかを指定するフラグ。この値のデフォルトはfalseです。

initialContextFactory

接続ファクトリの作成にEJBコンテナが使用する初期コンテキスト・ファクトリ。この値のデフォルトはweblogic.jndi.WLInitialContextFactoryです。

initSuspendSeconds

EJBコンテナがJMSリソースの停止を検出したときにMDBのJMS接続を中断する初期秒数。この値は任意の整数値に設定でき、デフォルトは5です。

jmsClientId

JMS宛先に接続するときのMDBのクライアントID。この値は、JMSトピックへの恒久サブスクリプションに使用されます。

jmsPollingIntervalSeconds

アクセスできなくなっているJMS宛先にEJBコンテナが再接続を試みる間隔(秒単位)。この値は任意の整数値に設定でき、デフォルトは10です。

maxBeansInFreePool

空きプール内の非アクティブMDBの最大数。この値は任意の正の整数値または0に設定できます。この値のデフォルトは1000です。

maxMessagesInTransaction

MDBのトランザクションに入れることができるメッセージの最大数。この値は任意の正の整数値または0に設定できます。この値のデフォルトは1です。

maxSuspendSeconds

EJBコンテナがJMSリソースの停止を検出したときにMDBのJMS接続を中断する最大秒数。この値は任意の整数に設定でき、デフォルトは60です。

messageSelector

ヘッダー・フィールド参照およびプロパティ参照ごとに、受信するメッセージを指定するためにクライアントによって使用される文字列。ヘッダーとプロパティ値が指定したセレクタに一致するメッセージのみが送信されます。この値は、メッセージ・ヘッダー、またはメッセージ・プロパティを使用した条件式に設定できます。この値のデフォルトはnullです。

providerURL

InitialContextで使用されるURLプロバイダ(通常はhost:port)。この値は、任意の有効なURLに設定でき、デフォルトはnullです。

subscriptionDurability

JMSトピック・サブスクリプションがDurableまたはNonDurableかを指定するフラグ。この値のデフォルトはDurableです。

topicMessagesDistributionMode

トピック・メッセージの配信モード。有効な値は、One-Copy-Per-Application、One-Copy-Per-Server、Compatibiltyです。この値のデフォルトはCompatibilityです。有効な値の詳細は、『Oracle WebLogic ServerメッセージドリブンBeanの開発』のトピックのデプロイメントのシナリオに関する項を参照してください。

transAttribute

メソッドの呼出しをエンタープライズBeanのビジネス・メソッドに委託するときにコンテナがトランザクションの境界をどのように管理するのかを指定するトランザクション設定。有効な値は、Required、NotSupported、Supports、RequiresNew、MandatoryおよびNeverです。この値のデフォルトはRequiredです。有効な値の詳細は、「Webサービス原子性トランザクションの使用」を参照してください。

transTimeoutSeconds

EJBのコンテナで開始されたトランザクションの最長継続時間(秒単位)。この時間を超えると、トランザクションはロールバックされ、サービスはSOAPフォルトを戻します。この値は任意の正の整数または0に設定できます。

トランザクション・タイムアウトが指定されていないか、0に設定されている場合、ドメインに構成されたトランザクション・タイムアウトが使用されます。ドメインにタイムアウトが構成されていない場合、デフォルトは30です。

use81StylePolling

WebLogic Serverバージョン8.1スタイルのポーリングの後方互換性をサポートするかどうかを指定するフラグ。有効な値は、TrueまたはFalseです。この値のデフォルトはFalseです。

構成メソッドと優先順位

必要に応じて、JMSトランスポートを有効にする際に、表17-8で定義するいずれかのメソッドを使用して、JMSトランスポート・プロパティを構成できます。

表17-8 JMSプロパティの構成に使用されるメソッド

構成メソッド

説明

JMSTransportClientFeature API

Webサービス・クライアントを作成し、JMSトランスポート・プロパティを引数としてweblogic.jws.jaxws.client.JmsTransportClientFeature APIに渡します。詳細は、「JMSトランスポートを使用したWebLogic Webサービスの呼出し」を参照してください。

ターゲット・サービス・エンドポイント・アドレス

ターゲット・サービス・エンドポイント・アドレスを構築し、JMSトランスポート・プロパティを問合せ文字列の一部として含めます。詳細は、「JMS URIの構成」を参照してください。

@JMSTransportClientアノテーション

Webサービス・クライアントを作成し、JMSトランスポート・プロパティを属性としてJWSファイルの@com.oracle.webservices.api.jms.JMSTransportClientアノテーションに渡します(「@JMSTransportClientアノテーションの使用」を参照)。

@JMSTransportServiceアノテーション

Webサービス・クライアントを作成し、JMSトランスポート・プロパティを属性としてJWSファイルの@com.oracle.webservices.api.jms.JMSTransportServiceアノテーションに渡します(「@JMSTransportServiceアノテーションの使用」を参照)。

clientgen Antタスクの<jmstransportclient>要素

clientgen Antタスクに<jmstransportclient>要素を含むWebサービスを構築します。詳細は、「Ant build.xmlファイルでの<jmstransportclient>要素の使用」を参照してください。

jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

jwsc Antタスクの<jws>要素に<jmstransportservice>子要素を含むWebサービスを構築します。詳細は、「Ant build.xmlファイルでの<jmstransportservice>子要素の使用」を参照してください。

WSDL

JMSトランスポート・プロパティ要素を含むWSDLからWebサービスを作成します(「WSDLでのJMSトランスポート・プロパティの構成」を参照)。

管理コンソール

WebLogic Server管理コンソールを使用して、デプロイされたWebサービスのJMSトランスポート・プロパティを構成します(「管理コンソールを使用したJMSトランスポートの構成」を参照)。

weblogic-webservices.xmlデプロイメント記述子の<soapjms-service-endpoint-address>要素

weblogic-webservices.xmlデプロイメント記述子は手動で更新できます。ただしこれはお薦めしません。<soapjms-service-endpoint-address要素の詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebLogic Webサービス・デプロイメント記述子のスキーマ・リファレンスに関する項を参照してください。

設計時および実行時におけるWebサービスまたはクライアントでのJMSトランスポート・プロパティ構成の優先順位を次にまとめます。

- 設計時のWebサービス(優先度の高い方から)

- jwsc Antタスクの<jws>要素内の<jmstransportservice>子要素

- @JMSTransportServiceアノテーション

- 実行時のWebサービス(優先度の高い方から)

- 管理コンソール

- weblogic-webservices.xmlデプロイメント記述子の<soapjms-service-endpoint-address>要素

- @JMSTransportServiceアノテーション

- 設計時のクライアント(優先度の高い方から)

- clientgenの<jmstransportclient>子要素

- WSDLで定義されたJMSトランスポート・プロパティ

- 実行時のクライアント(優先度の高い方から)

- JMS URIサービス・エンドポイント・アドレス

- JMSTransportClientFeature API

- @JMSTransportClientアノテーション

管理コンソールを使用したJMSトランスポートの構成

JMSトランスポートを有効にしてWebサービスをデプロイしたら、WebLogic Server管理コンソールを使用してJMSトランスポート・プロパティを構成できます。

WebLogic Server管理コンソールを使用してJMSトランスポート・プロパティを構成するには:

1. 『Oracle WebLogic Server WebLogic Webサービスの理解』の管理コンソールの呼出しに関する項の説明に従って、WebLogic Server管理コンソールを呼び出します。

2. 左側のナビゲーション・ペインで、「デプロイメント」を選択します。

3. 「デプロイメント」表でWebサービスの名前をクリックします。

4. 「構成」タブ、「ポート・コンポーネント」タブの順に選択します。

5. 「ポート」表でWebサービスのエンドポイントの名前をクリックします。

6. 「SOAP over JMSトランスポート」タブを選択します。

7. 必要に応じて、SOAP over JMSトランスポート構成のカスタマイズをクリックし、指示に従ってデプロイメント・プランを保存します。

8. 「JMSトランスポート・プロパティの構成」の説明に従って、SOAP over JMSトランスポート・プロパティを編集します。

9. 「保存」をクリックします。

詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのSOAP over JMSトランスポートの構成に関する項を参照してください。

WLSTを使用したJMSトランスポートの構成

WLSTを使用してJMSトランスポートを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

JMS URIの構成

接続トランスポートとしてSOAP over JMSを使用するようにWebLogic Webサービスを構成した場合、Webサービスの生成済WSDLで対応するポートに対して指定されたエンドポイント・アドレスのURLでは、http://ではなくjms:が使用されます。

JMS URIフォーマットは次のとおりです。

jms:lookupVariant:destinationName[?targetService=value[&property=value][&property=value]...
]

JMS URIは次のように構成されます。

- 接頭辞jms:

- ルックアップ・バリアント・タイプ(jndiに設定する必要があります)

- JMS宛先名(destinationName)

- JMSエンドポイント情報の指定に使用するプロパティと値のペアのリストが含まれる問合せ文字列。Webサービスのポート・コンポーネント名を定義するには、targetServiceプロパティを指定する必要があります。
その他の有効なプロパティは次のとおりです。

- bindingVersion

- deliveryMode

- deliveryType

- jndiConnectionFactoryName

- jndiContextParameter

- jndiInitialContextFactory

- jndiURL

- messageType

- priority

- replyToName

- timeToLive

JMSエンドポイント・アドレスには、lookupVariant、destinationNameおよびtargetServiceのJMSプロパティが必要です。

JMS URIを構成するJMSトランスポート・プロパティの詳細は、表17-6を参照してください。必要に応じて、JMSトランスポートを有効にする際に、表17-7で定義するいずれかのメソッドを使用して、JMSトランスポート・プロパティを構成できます。

例:

JMSエンドポイント・アドレスの例を次に示します。この例では、JMS宛先はmyQueue、Webサービスのポート・コンポーネントの名はWarehouseServicePortです。

jms:jndi:myQueue?targetService=WarehouseServicePort

次の例は、レスポンス・メッセージが送信されるJMS宛先のJNDI名を指定するreplyToNameプロパティが設定された、同じJMSエンドポイント・アドレスを示しています。

jms:jndi:myQueue?targetService=WarehouseServicePort&replyToName=myReplyToQueue

次の例は、jndi-com.acme.jndi.enable.tracingやjndi-java.naming.referralなど、追加のJNDI環境プロパティを指定する方法を示しています。

jms:jndi:myQueue?targetService=WarehouseServicePort&jndi-com.acme.jndi.enable.tracing=true&jndi-java.naming.referral=ignore

JMSリクエストURIの構成

各JMSトランスポート・メッセージには、JMS URIから派生する、SOAPJMS_requestURIとして定義されるメッセージ・プロパティがあります。JMSリクエストURIは、JMS URIを使用し、問合せパラメータを削除して構成します。

JMSリクエストURIフォーマットは次のとおりです。

jms:lookupVariant:destinationName

JMSリクエストURIは次のように構成されます。

- 接頭辞jms:

- ルックアップ・バリアント・タイプ(jndiに設定する必要があります)

- JMS宛先名(destinationName)

JMSリクエストURIを構成するJMSトランスポート・プロパティの詳細は、表17-6を参照してください。必要に応じて、JMSトランスポートを有効にする際に、表17-7で定義するいずれかのメソッドを使用して、JMSトランスポート・プロパティを構成できます。

例:

JMSエンドポイント・アドレスの例を次に示します。この例で、JMS宛先はmyQueueです。

jms:jndi:myQueue

WS-Addressingヘッダーの構成

SOAP over JMSトランスポートを使用するWebサービスおよびクライアントは、リクエストおよびレスポンス・メッセージのWS-AddressingヘッダーToおよびReplyToに、JMS URIから派生する値を移入します。

WS-Addressingヘッダー・フォーマットは次のとおりです。

jms:lookupVariant:destinationName?targetService=value

WS-Addressingヘッダーを構成するJMSトランスポート・プロパティの詳細は、表17-6を参照してください。必要に応じて、JMSトランスポートを有効にする際に、表17-7で定義するいずれかのメソッドを使用して、JMSトランスポート・プロパティを構成できます。

例:

SOAPリクエスト・メッセージのWS-Addressingヘッダーの例を次に示します。

<S:Header>
<To xmlns="http://www.w3.org/2005/08/addressing">
jms:jndi:myQueue?targetService=WarehouseService
</To>
<Action xmlns="http://www.w3.org/2005/08/addressing">
http://www.oracle.com/samples/ShipGoodsRequest
</Action>
<ReplyTo xmlns="http://www.w3.org/2005/08/addressing">
<Address>jms:jndi:myReplyToQueue?targetService=WarehouseService</Address>
</ReplyTo>
<MessageID xmlns="http://www.w3.org/2005/08/addressing">
uuid:3b9e7b20-3aa0-4a4a-9422-470fa7b9ada1
</MessageID>
</S:Header>

SOAPレスポンス・メッセージのWS-Addressingヘッダーの例を次に示します。

<S:Header>
<To xmlns="http://www.w3.org/2005/08/addressing">
jms:jndi:myReplyToQueue?targetService=WarehouseService
</To>
<Action xmlns="http://www.w3.org/2005/08/addressing">
http://www.oracle.com/samples/ShipGoodsResponse
</Action>
<MessageID xmlns="http://www.w3.org/2005/08/addressing">
uuid:9d0be951-79fc-4a56-b3e6-4775bde2bd82
</MessageID>
<RelatesTo xmlns="http://www.w3.org/2005/08/addressing">
uuid:3b9e7b20-3aa0-4a4a-9422-470fa7b9ada1
</RelatesTo>
</S:Header>

JMSレスポンス・キューの構成

双方向動作の場合、デフォルトで一時レスポンス・キューが生成されます。デフォルトの一時レスポンス・キューを使用することで、必要となる構成が最小限に抑えられます。ただし、サーバーの障害時には、レスポンス・メッセージが失われる可能性があります。

サーバーの再起動後にも使用可能な、永続JMSレスポンス・キューを構成できます。永続JMSレスポンス・キューには、次の利点があります。

- サーバーの再起動に続いてレスポンス・メッセージを確実にリストアできます。

- パフォーマンスを向上させ、最初の呼出しで一時キューの作成に必要なオーバーヘッドを回避します。

- サービス品質(QoS)の向上のためのキューの構成が可能です。

次の方法(優先度の高い順にリスト)のいずれかを使用して、JMSレスポンス・キューを構成できます。

- AsyncClientTransportFeatureを使用してaddressまたはReplyToヘッダーを構成する(「非同期クライアント・トランスポート機能の有効化と構成」を参照)。

- 次のいずれかの方法を使用してreplyToNameプロパティを構成する。

- clientgenの<jmstransportclient>要素(「Ant build.xmlファイルでの<jmstransportclient>要素の使用」を参照)。

- ターゲット・エンドポイント・アドレス(「ターゲット・エンドポイント・アドレスとしてのJMS URIの構成」を参照)。

- JMSTransportClientFeature(「JMSTransportClientFeatureクライアントAPIの使用」を参照)。

- @JMSTransportClientアノテーション(「@JMSTransportClientアノテーションの使用」を参照)。

注意:
destinationNameプロパティが匿名に設定されている場合(JMSトランスポートでは、これはサポートされていません)は、一時レスポンス・キューが使用されます。

JMSレスポンス・キューは、デフォルトで、JMSトランスポート・サービス呼出しのフォルト・キューとして使用されます。faultToヘッダーは、AsyncClientTransportFeatureを使用して構成できます(「非同期レスポンス・エンドポイントのReplyToヘッダーとFaultToヘッダーの構成」を参照)。

JMSメッセージ・タイプの構成

リクエスト・メッセージで使用する次のメッセージ・タイプのいずれかを構成できます。

- com.oracle.webservices.api.jms.JMSMessageType.BYTES: JMSメッセージの本体はバイナリ・データです。これがデフォルトです。

- com.oracle.webservices.api.jms.JMSMessageType.TEXT: JMSメッセージの本体は文字列データです。

messageTypeプロパティは、表17-8で定義されているいずれかの構成メソッドを使用して構成できます。

Webサービスでは、レスポンスの送信時に同じメッセージ・タイプを使用します。リクエストはBYTESとして受信され、応答はBYTESとして送信されます。

messageTypeプロパティをTEXTに設定する場合、次の点に注意してください。

- 大きなペイロードの場合、メモリー内表現のデータ要件が大きくなるため、TEXTメッセージのメモリー要件は、BYTESメッセージよりはるかに大きくなります。

- バイナリ添付ファイルのあるメッセージはbase64エンコードされる必要があり、これによってもメッセージのサイズが大幅に増加する可能性があります。

WSDLファイルへのHTTPアクセスの構成

デフォルトで、デプロイされたWebサービスのWSDLは、依然としてHTTPを使用してアクセス可能です。WSDLファイルへのアクセスを無効にする場合(特に、ファイアウォールの外でWebサービスにアクセスできる場合)は、次のいずれかを実行します。

- <jws>要素の<jmstransportservice>子要素のenableHttpWsdlAccess属性を使用します(「Ant build.xmlファイルでの<jmstransportservice>子要素の使用」を参照)。

- @JMSTransportServiceアノテーション(「@JMSTransportServiceアノテーションの使用」を参照)。

- Webサービスをデプロイした後に、WebLogic Server管理コンソールを使用してWSDLファイルへのアクセスを無効にします。この場合、構成情報は、アノテーションではなくデプロイメント・プラン内に格納されます。
このタスクをWebLogic Server管理コンソールを使用して実行する場合は、デプロイしたWebサービスの「構成」→「全般」ページに移動し、「動的WSDLの表示を有効化」チェック・ボックスの選択を解除します。この変更を有効にするには、構成をデプロイメント・プランに保存した後に、Webサービス(またはそのエンタープライズ・アプリケーション)を再デプロイ(更新)する必要があります。

SOAP Over JMSトランスポートの監視

次の観点から、SOAP over JMSトランスポートを使用するWebサービスを監視できます。

- Webサービス・パフォーマンスの監視。次を参照してください。

- Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービスの監視に関する項

- 『Webサービスの管理』のWebサービスの監視と監査に関する項

- JMS宛先メトリックの監視(『Oracle WebLogic Server JMSリソースの管理』のJMS統計の監視とメッセージの管理に関する項を参照)。

18 SOAPメッセージ・ハンドラの作成と使用

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic WebサービスでSOAPメッセージ・ハンドラを作成および使用する方法について説明します。

この章の内容は次のとおりです:

- SOAPメッセージ・ハンドラの概要

- サーバー側SOAPメッセージ・ハンドラの追加:主な手順

- クライアント側SOAPメッセージ・ハンドラの追加:主な手順

- SOAPメッセージ・ハンドラおよびハンドラ・チェーンの設計

- SOAPメッセージ・ハンドラの作成

- JWSファイルでのハンドラ・チェーンの構成

- ハンドラ・チェーン構成ファイルの作成

- Webサービスのコンパイルと再ビルド

- クライアント側SOAPメッセージ・ハンドラの構成

SOAPメッセージ・ハンドラの概要

Webサービスおよびそのクライアントは、メッセージのリクエストやレスポンスの追加処理において、SOAPメッセージにアクセスする必要が生じることがあります。SOAPメッセージ・ハンドラは、Webサービスのリクエストとレスポンスの両方でSOAPメッセージをインターセプトするメカニズムです。SOAPメッセージ・ハンドラを作成すると、WebサービスおよびクライアントがSOAPメッセージの追加処理を実行できるようになります。

ハンドラ使用の簡単な例としては、SOAPメッセージのヘッダー部分の情報へのアクセスがあります。SOAPのヘッダーを使用してWebサービス固有の情報を格納しておき、ハンドラを使用してその情報を操作することができます。

SOAPメッセージ・ハンドラは、Webサービスのパフォーマンスを向上させるために使用することもできます。Webサービスがデプロイされてしばらくすると、同じパラメータを使用してWebサービスを呼び出すコンシューマが多いことに気付く場合があります。よく使用されるWebサービス呼出しの結果をキャッシュしておき(結果が静的であることが前提となります)、適宜、キャッシュしておいた結果をただちに戻すことによって、Webサービスを実装したバックエンド・コンポーネントを呼び出す必要がなくなり、Webサービスのパフォーマンスが向上します。このパフォーマンスの向上は、ハンドラを使用して、SOAPリクエスト・メッセージに頻繁に使用されるパラメータが含まれていないかチェックすることで実現できます。

JAX-WSでは、SOAPハンドラと論理ハンドラという2つのタイプのSOAPメッセージ・ハンドラがサポートされます。SOAPハンドラは、メッセージのヘッダーや本文を含め、SOAPメッセージ全体にアクセスできます。論理ハンドラは、メッセージのペイロードにのみアクセスでき、メッセージ内のプロトコル固有の情報(たとえばヘッダー)を変更することはできません。

注意:
SOAPハンドラは、インバウンド・メッセージに(セキュリティ、WS-ReliableMessaging、MTOMなど)ポリシーと一緒に使用した場合、ユーザー定義のメッセージ・ハンドラの実行前に、ポリシーのインターセプタが実行されます。アウトバウンド・メッセージの場合、この順序は逆になります。

サーバー側SOAPメッセージ・ハンドラの追加:主な手順

次の手順では、WebサービスにSOAPメッセージ・ハンドラを追加する手順を大まかに説明します。

Webサービスを実装する基本的なJWSファイルを作成済であり、SOAPメッセージ・ハンドラおよびハンドラ・チェーンを追加してWebサービスを更新することが前提となっています。また、Antベースの開発環境を設定済であり、かつjwsc Antタスクを実行するためのターゲットを含む、作業用のbuild.xmlファイルがあることも前提となっています。詳細については、以下を参照してください。

- 第3章「JAX-WS Webサービスの開発」

- 第4章「JWSファイルのプログラミング」

- 第8章「Webサービス・クライアントの開発」

表18-1 WebサービスへのSOAPメッセージ・ハンドラの追加手順

#

手順

説明

1

ハンドラとハンドラ・チェーンを設計します。

SOAPメッセージ・ハンドラを設計し、ハンドラ・チェーン内でグループ化します。「SOAPメッセージ・ハンドラおよびハンドラ・チェーンの設計」を参照してください。

2

ハンドラ・チェーン内のハンドラごとに、SOAPメッセージ・ハンドラ・インタフェースを実装するJavaクラスを作成します。

「SOAPメッセージ・ハンドラの作成」を参照してください。

3

SOAPメッセージ・ハンドラを構成するためのアノテーションを追加して、JWSファイルを更新します。

「JWSファイルでのハンドラ・チェーンの構成」を参照してください。

4

ハンドラ・チェーン構成ファイルを作成します。

「ハンドラ・チェーン構成ファイルの作成」を参照してください。

5

ハンドラ・チェーン内のすべてのハンドラ・クラスをコンパイルし、Webサービスを再ビルドします。

「Webサービスのコンパイルと再ビルド」を参照してください。

クライアント側SOAPメッセージ・ハンドラの追加:主な手順

クライアント側SOAPメッセージ・ハンドラは、スタンドアロン・クライアント用にも、WebLogic Server内部で実行されるクライアント用にも構成できます。実際のJavaクライアント側ハンドラは、サーバー側ハンドラと同じ方法、つまり、SOAPメッセージ・ハンドラ・インタフェースを実装するJavaクラスを作成する方法で作成できます。多くの場合、WebLogic Serverで実行されるWebサービスとそのWebサービスを呼び出すクライアント・アプリケーションで、同じハンドラ・クラスを使用できます。たとえば、サーバーおよびクライアント用として、送信および受信したすべてのSOAPメッセージをログに記録する汎用ロギング・ハンドラ・クラスを記述できます。

次の手順では、Webサービス操作を呼び出すクライアント・アプリケーションにクライアント側SOAPメッセージ・ハンドラを追加する手順を大まかに説明します。

デプロイされたWebサービスを呼び出すクライアント・アプリケーションを作成済であり、クライアント側SOAPメッセージ・ハンドラおよびハンドラ・チェーンを追加してクライアント・アプリケーションを更新することを想定しています。また、Antベースの開発環境を設定済であり、かつclientgen Antタスクを実行するためのターゲットを含む、作業用のbuild.xmlファイルがあることが前提となっています。詳細は、「Java SEクライアントからのWebサービスの呼出し」を参照してください。

表18-2 Webサービス・クライアントにSOAPメッセージ・ハンドラを追加する手順

#

手順

説明

1

ハンドラとハンドラ・チェーンを設計します。

この手順は、サーバー側SOAPメッセージ・ハンドラを設計する手順と似ていますが、視点がWebサービスからではなくクライアント・アプリケーションからとなる点が異なります。「SOAPメッセージ・ハンドラおよびハンドラ・チェーンの設計」を参照してください。

2

ハンドラ・チェーン内のハンドラごとに、SOAPメッセージ・ハンドラ・インタフェースを実装するJavaクラスを作成します。

この手順は、サーバー側SOAPメッセージ・ハンドラを設計する手順と似ていますが、視点がWebサービスからではなくクライアント・アプリケーションからとなる点が異なります。ハンドラ・クラスのプログラミングの詳細は、「SOAPメッセージ・ハンドラの作成」を参照してださい。

3

クライアントを更新して、SOAPメッセージ・ハンドラをプログラム的に構成します。

「クライアント側SOAPメッセージ・ハンドラの構成」を参照してください。

4

アプリケーションのビルドに使用するbuild.xmlファイルを更新して、clientgen Antタスクにカスタマイズ・ファイルを指定します。

「Webサービスのコンパイルと再ビルド」を参照してください。

5

適切なタスクを実行して、クライアント・アプリケーションを再ビルドします。

prompt> ant build-client

次回クライアント・アプリケーションを実行したときには、SOAPリクエスト・メッセージの送信前とレスポンスの受信後に、構成ファイルに記述したSOAPメッセージ・ハンドラが自動的に実行されます。

注意:
clientgen Antタスクにハンドラの構成ファイルが指定されている限り、クライアント側SOAPメッセージ・ハンドラを呼び出すために実際のクライアント・アプリケーションを更新する必要はありません。ハンドラは、生成されたインタフェースによって自動的に正しい順序で実行されます。

SOAPメッセージ・ハンドラおよびハンドラ・チェーンの設計

SOAPメッセージ・ハンドラを設計するときには、以下の事項を決定する必要があります。

- 作業を実行するために必要なハンドラの数

- 実行の順序

ハンドラ・チェーン内でSOAPメッセージ・ハンドラをグループ化します。ハンドラ・チェーン内の各ハンドラには、インバウンド・メッセージとアウトバウンド・メッセージ両方のメソッドを定義できます。

ただし、インバウンド・メッセージとアウトバウンド・メッセージで同じタイプの処理が必要となるため、通常は各SOAPメッセージ・ハンドラにリクエストSOAPメッセージとレスポンスSOAPメッセージを処理する別個のメソッドを定義します。一方、SOAPリクエストのみを処理し、それと同等のレスポンス処理は行わないハンドラを設計することもできます。また、ハンドラ・チェーン内の次のハンドラを呼び出さず、そのまま、任意の時点でクライアント・アプリケーションにレスポンスを送信することも可能です。

サーバー側ハンドラの実行

Webサービスを呼び出すときに、WebLogic Serverは次のようにハンドラを実行します。

1. ハンドラ・チェーン内のハンドラのinboundメソッドはすべて、JWSアノテーションで指定されている順序で実行されます。これらのinboundメソッドのいずれもが、SOAPのリクエスト・メッセージを変更できます。

2. ハンドラ・チェーン内の最後のハンドラが実行されると、WebLogic Serverは、Webサービスを実装するバックエンド・コンポーネントを呼び出し、最終的なSOAPのリクエスト・メッセージを渡します。

3. バックエンド・コンポーネントの実行が終了したら、ハンドラ・チェーン内のハンドラのoutboundメソッドが、JWSアノテーションで指定されているのとは逆の順序で実行されます。これらのoutboundメソッドのいずれもが、SOAPのレスポンス・メッセージを変更できます。

4. ハンドラ・チェーン内の最初のハンドラが実行されると、WebLogic Serverは、Webサービスを呼び出したクライアント・アプリケーションに最終的なSOAPレスポンス・メッセージを戻します。

たとえば、JWSファイルで@HandlerChain JWSアノテーションを使用して外部構成ファイルを指定することになっており、その構成ファイルでは、次の例に示す3つのハンドラが格納されたSimpleChainというハンドラ・チェーンを定義していると仮定します。

<?xml version="1.0" encoding="UTF-8" ?>
<handler-chains xmlns="http://java.sun.com/xml/ns/javaee">
<handler-chain>
<handler>
<handler-class>
Handler1
</handler-class>
</handler>
</handler-chain>
<handler-chain>
<handler>
<handler-class>
Handler2
</handler-class>
</handler>
</handler-chain>
<handler-chain>
<handler>
<handler-class>
Handler3
</handler-class>
</handler>
</handler-chain>
</handler-chains>

次の図は、WebLogic Serverで各ハンドラのinboundメソッドとoutboundメソッドが実行される順序を示しています。

図18-1 ハンドラ・メソッドの実行順序

クライアント側ハンドラの実行

クライアント側ハンドラの場合は、以下のタイミングで二度実行されます。

- クライアント・アプリケーションがWebサービスにSOAPリクエストを送信する直前

- クライアント・アプリケーションがWebサービスからSOAPレスポンスを受信した直後

SOAPメッセージ・ハンドラの作成

SOAPメッセージ・ハンドラには2つのタイプがあります。次の表にそれぞれの定義を示します。

表18-3 SOAPメッセージ・ハンドラのタイプ

ハンドラ・タイプ

説明

SOAPハンドラ

ヘッダーを含めたSOAPメッセージ全体へのアクセスを可能にします。SOAPハンドラは、javax.xml.ws.handler.soap.SOAPHandlerインタフェースを使用して定義します。呼出しには、javax.xml.ws.handler.MessageContextを拡張したjavax.xml.ws.handler.soap.SOAPMessageContextのインポートを使用します。SOAPMessageContext.getMessage()メソッドは、javax.xml.soap.SOAPMessageを返します。

論理ハンドラ

メッセージのペイロードへのアクセスを提供します。メッセージ内のプロトコル固有の情報(たとえばヘッダー)を変更することはできません。論理ハンドラは、javax.xml.ws.handler.LogicalHandlerインタフェースを使用して定義します。(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/LogicalHandler.htmlを参照)。呼出しには、javax.xml.ws.handler.MessageContextを拡張したjavax.xml.ws.handler.LogicalMessageContextを使用します。LogicalMessageContext.getMessage()メソッドは、javax.xml.ws.LogicalMessageを返します。

ペイロードには、JAXBオブジェクトまたはjavax.xml.transform.Sourceオブジェクトとしてアクセスできます。(http://docs.oracle.com/javaee/6/api/javax/xml/ws/LogicalMessage.htmlを参照)。

両方のタイプのメッセージ・ハンドラが拡張するjavax.xml.ws.Handlerインタフェースは、次の表に示すメソッドを定義します。(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/Handler.htmlを参照)。

表18-4 ハンドラ・インタフェース・メソッド

メソッド

説明

handleMessage()

インバウンドおよびアウトバウンド・メッセージの通常処理を管理します。MessageContextオブジェクトのプロパティは、メッセージがインバウンドか発信かを識別するために使用します。「Handler.handleMessage()メソッドの実装」を参照してください。

handleFault()

インバウンドおよびアウトバウンド・メッセージのフォルト処理を管理します。「Handler.handleFault()メソッドの実装」を参照してください。

close()

メッセージ交換を完了し、処理の間にアクセスしたリソースをクリーンアップします。「Handler.close()メソッドの実装」を参照してください。

また、@javax.annotation.PostConstructおよび@javax.annotation.PreDestroyアノテーションを使用すると、ハンドラが作成された後に実行するメソッドとハンドラが破棄される前に実行するメソッドを指定できます。

特に画像などの添付ファイルを処理する場合などには、ハンドラ内から直接SOAPメッセージを表示または更新しなければならない場合もあります。この場合は、http://java.net/projects/saaj/のSOAP With Attachments API for Java 1.1 (SAAJ)仕様の構成要素であるjavax.xml.soap.SOAPMessage抽象クラスを使用します。詳細は、「SAAJを使用したSOAPリクエスト・メッセージおよびレスポンス・メッセージの直接操作」を参照してください。

SOAPハンドラのサンプル

次に、単純なSOAPハンドラのサンプルを示します。このハンドラは、メッセージの内容とともに、メッセージがインバウンドかアウトバウンドかを返します。

package examples.webservices.handler;

import java.util.Set;
import java.util.Collections;
import javax.xml.namespace.QName;
import javax.xml.ws.handler.soap.SOAPHandler;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.handler.soap.SOAPMessageContext;
import javax.xml.soap.SOAPMessage;

public class Handler1 implements SOAPHandler<SOAPMessageContext>
{
public Set<QName> getHeaders()
{
return Collections.emptySet();
}

public boolean handleMessage(SOAPMessageContext messageContext)
{
Boolean outboundProperty = (Boolean)
messageContext.get (MessageContext.MESSAGE_OUTBOUND_PROPERTY);

if (outboundProperty.booleanValue()) {
System.out.println("\nOutbound message:");
} else {
System.out.println("\nInbound message:");
}

System.out.println("** Response: "+messageContext.getMessage().toString());
return true;
}

public boolean handleFault(SOAPMessageContext messageContext)
{
return true;
}

public void close(MessageContext messageContext)
{
}
}

論理ハンドラのサンプル

次に、単純な論理ハンドラのサンプルを示します。このハンドラは、メッセージの内容とともに、メッセージがインバウンドかアウトバウンドかを返します。

package examples.webservices.handler;

import java.util.Set;
import java.util.Collections;
import javax.xml.namespace.QName;
import javax.xml.ws.handler.LogicalHandler;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.handler.LogicalMessageContext;
import javax.xml.ws.LogicalMessage;
import javax.xml.transform.Source;

public class Handler2 implements LogicalHandler<LogicalMessageContext>
{
public Set<QName> getHeaders()
{
return Collections.emptySet();
}

public boolean handleMessage(LogicalMessageContext messageContext)
{
Boolean outboundProperty = (Boolean)
messageContext.get (MessageContext.MESSAGE_OUTBOUND_PROPERTY);
if (outboundProperty.booleanValue()) {
System.out.println("\nOutbound message:");
} else {
System.out.println("\nInbound message:");
}

System.out.println("** Response: "+messageContext.getMessage().toString());
return true;
}

public boolean handleFault(LogicalMessageContext messageContext)
{
return true;
}

public void close(MessageContext messageContext)
{
}
}

Handler.handleMessage()メソッドの実装

Handler.handleMessage()メソッドは、バックエンド・コンポーネントによって処理される前および後に、SOAPのリクエスト・メッセージをインターセプトするために呼び出されます。そのシグネチャは次のとおりです。

public boolean handleMessage(C context)
throws java.lang.RuntimeException, java.xml.ws.ProtocolException {}

このメソッドを実装すると、バックエンド・コンポーネントによって処理される前および後に、SOAPメッセージ内のデータの暗号化/復号化などのタスクを実行できます。

Cは、javax.xml.ws.handler.MessageContextを拡張します(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/MessageContext.htmlを参照)。ハンドラ・チェーン内のハンドラは、MessageContextプロパティを使用して、メッセージがインバウンドかアウトバウンドかを識別し、処理状態を共有します。MessageContextのSOAPMessageContextまたはLogicalMessageContextサブインタフェースを使用すると、SOAPメッセージまたは論理メッセージの内容を取得したり設定したりできます。詳細については、「メッセージ・コンテキスト・プロパティの値とメソッドの使用」を参照してください。

SOAPメッセージのすべての処理をコーディングしたら、以下のシナリオのいずれかをコーディングします。

- trueを返すことにより、ハンドラ・リクエスト・チェーン内の次のハンドラを呼び出します。
リクエスト・チェーンの次のハンドラは、@HandlerChainアノテーションによって指定された構成ファイル内の<handler-chain>要素の次の<handler>下位要素として指定されます。

- falseを返すことにより、ハンドラ・リクエスト・チェーンの処理をブロックします。
ハンドラ・リクエスト・チェーンの処理をブロックすると、Webサービスのこの呼出しについては、バックエンド・コンポーネントは実行されなくなります。Webサービスの一部の呼出しの結果をキャッシュしてあり、そのリストに現在の呼出しも含まれている場合は、この操作が便利な場合があります。

ハンドラ・リクエスト・チェーンの処理は中断されますが、WebLogic Serverが、現在のハンドラから順に、レスポンス・チェーンを呼び出します。

- ハンドラに固有のすべての実行時エラーに対して、java.lang.RuntimeExceptionまたはjava.xml.ws.ProtocolExceptionをスローします。
WebLogic Serverは、この例外を捕捉すると、ハンドラ・リクエスト・チェーンの後続の処理を終了し、この例外をWebLogic Serverのログ・ファイルに記録した上で、このハンドラのhandleFault()メソッドを呼び出します。

Handler.handleFault()メソッドの実装

Handler.handleFault()メソッドは、SOAPメッセージ処理モデルに基づいてSOAP障害を処理します。そのシグネチャは次のとおりです。

public boolean handleFault(C context)
throws java.lang.RuntimeException, java.xml.ws.ProtocolException{}

このメソッドを実装すると、バックエンド・コンポーネントによって生成されたフォルトのほか、handleMessage()メソッドによって生成されたあらゆるSOAPフォルトの処理も扱うことができます。

Cは、javax.xml.ws.handler.MessageContextを拡張します(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/MessageContext.htmlを参照)。ハンドラ・チェーン内のハンドラは、MessageContextプロパティを使用して、メッセージがインバウンドかアウトバウンドかを識別し、処理状態を共有します。MessageContextのLogicalMessageContextまたはSOAPMessageContextサブインタフェースを使用すると、SOAPメッセージまたは論理メッセージの内容を取得したり設定したりできます。詳細については、「メッセージ・コンテキスト・プロパティの値とメソッドの使用」を参照してください。

SOAPフォルトのすべての処理をコーディングしたら、次のいずれかを実行します。

- trueを返すことにより、ハンドラ・チェーン内の次のハンドラのhandleFault()メソッドを呼び出します。

- falseを返すことにより、ハンドラ・フォルト・チェーンの処理をブロックします。

Handler.close()メソッドの実装

Handler.close()は、メッセージ交換を完了し、処理の間にアクセスしたリソースをクリーンアップします。そのシグネチャは次のとおりです。

public boolean close(MessageContext context) {}

メッセージ・コンテキスト・プロパティの値とメソッドの使用

SOAPメッセージ・ハンドラには、以下のコンテキスト・オブジェクトが渡されます。

表18-5 メッセージ・コンテキスト・プロパティの値

メッセージ・コンテキスト・プロパティの値

説明

javax.xml.ws.handler.LogicalMessageContext

論理ハンドラのコンテキスト・オブジェクト

javax.xml.ws.handler.soap.SOAPMessageContext

SOAPハンドラのコンテキスト・オブジェクト

各コンテキスト・オブジェクトは、javax.xml.ws.handler.MessageContextを拡張します。これにより、SOAPメッセージ・ハンドラの実行時プロパティにクライアント・アプリケーションやWebサービスからアクセスするのみでなく、Webサービスのjavax.xml.ws.WebServiceContextから直接アクセスすることも可能になります(https://jax-ws.java.net/nonav/jax-ws-20-pfd/api/javax/xml/ws/WebServiceContext.htmlを参照)。

たとえば、MessageContext.MESSAGE_OUTBOUND_PROPERTYには、メッセージの方向を識別するために使用するBoolean値が格納されています。リクエストの間にこのプロパティの値をチェックすることで、メッセージがインバウンド・リクエストなのかアウトバウンド・リクエストなのかを識別できます。このプロパティは、クライアント側のハンドラからアクセスしたときはtrue、サーバー側のハンドラからアクセスしたときはfalseになります。

使用可能なMessageContextプロパティ値の詳細は、「MessageContextプロパティ値の使用」を参照してください。

LogicalMessageContextクラスは、論理メッセージを処理する次のメソッドを定義します。詳細は、Javadocの「java.xml.ws.handler.LogicalMessageContext」(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/LogicalMessageContext.html)を参照してください。

表18-6 LogicalMessageContextクラスのメソッド

メソッド

説明

getMessage()

SOAPメッセージを含むjavax.xml.ws.LogicalMessageオブジェクトを取得します。

SOAPMessageContextクラスは、SOAPメッセージを処理する次のメソッドを定義します。詳細は、Javadocの「java.xml.ws.handler.soap.SOAPMessageContext」(http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/soap/SOAPMessageContext.html)を参照してください。

注意:
SOAPメッセージ自体は、(http://docs.oracle.com/javaee/5/api/javax/xml/soap/SOAPMessage.html)のjavax.xml.soap.SOAPMessageオブジェクトに格納されています。このオブジェクトの詳細は、「SAAJを使用したSOAPリクエスト・メッセージおよびレスポンス・メッセージの直接操作」を参照してください。

表18-7 SOAPMessageContextクラスのメソッド

メソッド

説明

getHeaders()

メッセージ・コンテキスト内のメッセージから、特定の修飾名のヘッダーを取得します。

getMessage()

SOAPメッセージを含むjavax.xml.soap.SOAPMessageオブジェクトを取得します。

getRoles()

ハンドラ・チェーンの実行に関連付けられているSOAPアクター・ロールを取得します。

setMessage()

SOAPメッセージを設定します。

SAAJを使用したSOAPリクエスト・メッセージおよびレスポンス・メッセージの直接操作

javax.xml.soap.SOAPMessage抽象クラスは、(http://java.sun.com/webservices/saaj/docs.html)のSOAP With Attachments API for Java 1.1 (SAAJ)仕様の構成要素です。このクラスは、SOAPメッセージ・ハンドラ作成時にSOAPのリクエスト・メッセージおよびレスポンス・メッセージを操作するのに使用します。この節では、SOAPMessageオブジェクトの基本構造とSOAPメッセージの表示および更新に役立つメソッドのいくつかについて説明します。

SOAPMessageオブジェクトは、SOAPPartオブジェクト(SOAP XMLドキュメントそのものが入っています)、または同オブジェクトと添付ファイルで構成されています。

SOAPMessageクラスの詳細な説明については、SAAJに関するJavadocを参照してください。

SOAPPartオブジェクト

注意:
SOAPPartオブジェクトのsetContentメソッドおよびgetContentメソッドは、javax.xml.transform.stream.StreamSourceコンテンツのみをサポートします。これらのメソッドではjavax.xml.transform.dom.DOMSourceコンテンツはサポートされません。

SOAPPartオブジェクトには、SOAPEnvelopeオブジェクトに格納されたXML SOAPドキュメントが入っています。このオブジェクトは、実際のSOAPのヘッダーと本文を取得するのに使用します。

次のJavaコードのサンプルは、Handlerクラスによって提供されたMessageContextオブジェクトからSOAPメッセージを取り出して、その各部を参照する方法を示しています。

SOAPMessage soapMessage =  messageContext.getMessage();
SOAPPart soapPart = soapMessage.getSOAPPart();
SOAPEnvelope soapEnvelope = soapPart.getEnvelope();
SOAPBody soapBody = soapEnvelope.getBody();
SOAPHeader soapHeader = soapEnvelope.getHeader();

AttachmentPartオブジェクト

javax.xml.soap.AttachmentPartオブジェクト(http://docs.oracle.com/javaee/5/api/javax/xml/soap/AttachmentPart.htmlを参照)には、SOAPメッセージに対するオプションの添付ファイルが入っています。添付ファイルは、SOAPメッセージの残りの部分とは異なり、XMLフォーマットの必須部分ではないので、その形式は、単純なテキストからイメージ・ファイルまで、様々です。

注意:
SOAPメッセージ・ハンドラから直接に添付ファイルjava.awt.Imageにアクセスする場合は、「SOAPメッセージ・ハンドラで画像添付ファイルの操作」で重要情報を参照してください。

添付ファイルを操作するには、SOAPMessageクラスの次のメソッドを使用します。詳細は、Javadocの「javax.xml.soap.SOAPMessage」(http://docs.oracle.com/javaee/5/api/javax/xml/soap/SOAPMessage.html)を参照してください。

表18-8 添付ファイルの操作に使用するSOAPMessageクラスのメソッド

メソッド

説明

addAttachmentPart()

作成されたAttachmentPartオブジェクトをSOAPMessageに追加します。

countAttachments()

このSOAPメッセージに含まれている添付ファイルの数を返します。

createAttachmentPart()

他のタイプのObjectからAttachmentPartオブジェクトを作成します。

getAttachments()

すべての添付ファイルをAttachmentPartオブジェクトとして取得し、Iteratorオブジェクトに格納します。

SOAPメッセージ・ハンドラで画像添付ファイルの操作

この項では、添付ファイルjava.awt.ImageにアクセスするSOAPメッセージ・ハンドラを作成すること、およびclientgen Antタスクによって生成されたクライアントJAX-WSポートを使用するクライアント・アプリケーションからImageが送信されていることを前提としています。

clientgen Antタスクによって生成されたクライアント・コードでは、添付ファイルjava.awt.Imageはimage/gifではなくtext/xmlのMIMEタイプで、呼び出されるWebLogic Webサービスに送信され、画像は画像を表す整数のストリームにシリアライズされます。特に、このクライアント・コードは次の形式で画像をシリアライズします。

- int width

- int height

- int[] pixels

つまり、受信したImage添付ファイルを操作するSOAPメッセージ・ハンドラでは、このデータ・ストリームをデシリアライズして元の画像を作成し直す必要があるということです。

JWSファイルでのハンドラ・チェーンの構成

@javax.jws.HandlerChainアノテーションが(この章では、簡略化のために@HandlerChainとも言います)を使用すると、Webサービスのハンドラ・チェーンを構成できます。file属性を使用して、Webサービスと関連付けるハンドラ・チェーンの構成が含まれた外部ファイルを指定します。構成には、チェーン内のハンドラのリスト、ハンドラが実行される順序、初期化パラメータなどが含まれます。

次のJWSファイルでは、@HandlerChainアノテーションの使用例を示します。関連のJavaコードは太字で示しています。

package examples.webservices.handler;

import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.jws.HandlerChain;
import javax.annotation.Resource;
import javax.xml.ws.WebServiceContext;
@WebService(name = "Handler", targetNamespace = "http://example.org")
@HandlerChain(file="handler-chain.xml")
public class HandlerWS
{
@Resource
WebServiceContext ctx;
@WebMethod()
public String getProperty(String propertyName)
{
return (String) ctx.getMessageContext().get(propertyName);
}
}

このサンプルに示すように、@HandlerChainアノテーションを使用する前に、それをJWSファイルにインポートする必要があります。

@HandlerChainアノテーションのfile属性を使用し、ハンドラ・チェーンの構成情報を含む外部ファイルの名前を指定します。この属性の値はURLです。これは相対でも絶対でもかまいません。相対URLは、ファイルをコンパイルするためにjwsc Antタスクを実行した時点でのJWSファイルの場所を基準とします。

注意:
1つのJWSファイル内に複数の@HandlerChainアノテーションを指定すると、エラーになります。

外部構成ファイル作成の詳細は、「ハンドラ・チェーン構成ファイルの作成」を参照してください。

この項で説明した標準的なJWSアノテーションの詳細は、Web Services Metadata for the Java Platform仕様(http://www.jcp.org/en/jsr/detail?id=181)を参照してください。

ハンドラ・チェーン構成ファイルの作成

前の項で説明したように、Webサービスにハンドラ・チェーンを関連付けるには、JWSファイル内で@HandlerChainアノテーションを使用します。その際には、外部構成ファイルからなるハンドラ・チェーン・ファイルを作成し、ハンドラ・チェーン内のハンドラのリスト、ハンドラの実行順序、初期化パラメータなどを指定する必要があります。

このファイルはJWSファイルの外部にあるため、この単一の構成ファイルを複数のWebサービスで使用するように構成し、エンタープライズ内のすべてのWebサービスに関してハンドラ構成ファイルを標準化することができます。加えて、すべてのWebサービスを再コンパイルすることなく、ハンドラ・チェーンの構成を変更できます。

構成ファイルは、次の簡単なサンプルに示すように、XMLを使用して1つまたは複数のハンドラ・チェーンをリストします。

<?xml version="1.0" encoding="UTF-8"?>
<handler-chains xmlns="http://java.sun.com/xml/ns/javaee">
<handler-chain>
<handler>
<handler-class>examples.webservices.handler.Handler1</handler-class>
</handler>
</handler-chain>
<handler-chain>
<handler>
<handler-class>examples.webservices.handler.Handler2</handler-class>
</handler>
</handler-chain>
</handler-chains>

このサンプルでは、2つのハンドラが<handler-class>要素で指定したクラス名でハンドラ・チェーンに実装されています。2つのハンドラは、関連のWebサービス操作の前には昇順で実行され、操作実行後には逆順で実行されます。

ハンドラによって実装されるハンドラ初期化パラメータおよびSOAPロールを指定するには、それぞれ<handler>要素の<init-param>および<soap-role>子要素を使用します。

同じハンドラ・チェーンに、論理ハンドラとSOAPハンドラを含めることができます。ハンドラ・チェーンは実行時に再び並べ替えられ、アウトバウンド・メッセージではすべての論理ハンドラがSOAPハンドラより前に実行され、インバウンド・メッセージではすべてのSOAPハンドラが論理ハンドラより前に実行されます。

外部構成ファイルを定義するXMLスキーマ、その作成の詳細、および他のサンプルについては、Web Services Metadata for the Java Platform仕様(http://www.jcp.org/en/jsr/detail?id=181)を参照してください。

Webサービスのコンパイルと再ビルド

この項では、Webサービスをコンパイルおよびビルドする作業用のbuild.xml Antファイルがあり、そのビルド・ファイルを更新してハンドラ・チェーンを含めることを想定しています。このbuild.xmlファイルの作成については、「JAX-WS Webサービスの開発」を参照してください。

メッセージ・ハンドラのコンパイルとビルドが含まれるように開発環境を更新するには、以下のガイドラインに従います。

- JWSファイルに@HandlerChainアノテーションを追加したら、jwsc Antタスクを再実行してJWSファイルを再コンパイルし、新しいWebサービスを生成する必要があります。これは、JWSファイル内のアノテーションに変更を加えた場合は常に当てはまります。
JWSファイルで@HandlerChainアノテーションを使用し、jwsc Antタスクを再実行してWebサービスを再生成し、その後、外部構成ファイルのみを変更した場合は、2度目の変更を有効にするためにjwscを再実行する必要はありません。

- 以下の条件がすべて満たされていれば、jwsc AntタスクはSOAPメッセージ・ハンドラJavaファイルをハンドラ・クラスにコンパイル(およびその後それらを生成されたアプリケーションにパッケージ化)します。

- ハンドラ・クラスはJWSファイルの@HandlerChainアノテーションにおいて参照されます。

- Javaファイルはsourcepath属性で指定されたディレクトリ内に置かれます。

- クラスは現在CLASSPATH内に存在しません。

ハンドラ・クラスをjwscで自動的にコンパイルするのではなく、ユーザー側でコンパイルする場合は、jwsc Antタスクを実行する前に、コンパイルされたクラスがCLASSPATH内にあることを確認してください。

- ハンドラ・チェーンが関連付けられているWebサービスのデプロイおよび呼出しは、ハンドラ・チェーンのないWebサービスのデプロイおよび呼出しと同様に行います。唯一の相違点は、Webサービスのどの操作を呼び出す場合でも、WebLogic Webサービス・ランタイムは、操作呼出しの前と後の両方で、ハンドラ・チェーン内のハンドラを実行するということです。

クライアント側SOAPメッセージ・ハンドラの構成

クライアント側SOAPメッセージ・ハンドラは、以下のいずれかの方法で定義できます。

- ポート・ポリシーやjavax.xml.ws.Dispatchオブジェクトのように、ハンドラ・チェーンを直接javax.xml.ws.BindingProviderに設定します。例:

package examples.webservices.handler.client;

import javax.xml.namespace.QName;
import java.net.MalformedURLException;
import java.net.URL;

import javax.xml.ws.handler.Handler;
import javax.xml.ws.Binding;
import javax.xml.ws.BindingProvider;
import java.util.List;

import examples.webservices.handler.Handler1;
import examples.webservices.handler.Handler2;

public class Main {
public static void main(String[] args) {
HandlerWS test;
try {
test = new HandlerWS(new URL(args[0] + "?WSDL"), new
QName("http://example.org", "HandlerWS") );
} catch (MalformedURLException murl) { throw new RuntimeException(murl); }
HandlerWSPortType port = test.getHandlerWSPortTypePort();

Binding binding = ((BindingProvider)port).getBinding();
List<Handler> handlerList = binding.getHandlerChain();
handlerList.add(new Handler1());
handlerList.add(new Handler2());
binding.setHandlerChain(handlerList);
String result = null;
result = port.sayHello("foo bar");
System.out.println( "Got result: " + result );
}
}

- Serviceインスタンスにjavax.xml.ws.handler.HandlerResolverを実装します。例:

public static class MyHandlerResolver implements HandlerResolver {
public List<Handler> getHandlerChain(PortInfo portInfo) {
List<Handler> handlers = new ArrayList<Handler>();
// add handlers to list based on PortInfo information
return handlers;
}
}

setHandlerResolver()メソッドを使用して、Serviceインスタンスにハンドラ解決メカニズムを追加します。この場合は、Serviceインスタンスから作成されたポート・プロキシまたはDispatchオブジェクトで、HandlerResolverを使用してハンドラ・チェーンを特定します。例:

test.setHandlerResolver(new MyHandlerResolver());

- ハンドラ・チェーンの記述を格納する<binding>要素を含むカスタマイズ・ファイルを作成します。<handler-chains>要素のスキーマは、ハンドラ・チェーン・ファイル(サーバー上)とカスタマイズ・ファイルで同じものを使用します。例:

<bindings xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
wsdlLocation="http://localhost:7001/handler/HandlerWS?WSDL"
xmlns="http://java.sun.com/xml/ns/jaxws">
<bindings node="wsdl:definitions"
xmlns:jws="http://java.sun.com/xml/ns/javaee">
<handler-chains>
<handler-chain>
<handler>
<handler-class>examples.webservices.handler.Handler1
</handler-class>
</handler>
</handler-chain>
<handler-chain>
<handler>
<handler-class>examples.webservices.handler.Handler2
</handler-class>
</handler>
</handler-chain>
</handler-chains>
</bindings>

clientgenコマンドの<binding>子要素を使用してカスタマイズ・ファイルに渡します。

19 SOAPフォルトを使用した例外処理

この章では、メッセージがJava API for XML Web Services (JAX-WS)を使用するWebLogic Server 12.1.3用のWebLogic WebサービスのSimple Object Access Protocol (SOAP)フォルトを使用して処理される場合に発生する例外の処理方法について説明します。

この章の内容は次のとおりです:

- SOAPフォルトを使用した例外処理の概要

- SOAPフォルト要素のコンテンツ

- モデル化されたフォルトの使用

- モデル化されていないフォルトの使用

- 例外処理プロセスのカスタマイズ

- SOAPフォルトからのスタック・トレースの無効化

- その他の例外

SOAPフォルトを使用した例外処理の概要

Webサービス・リクエストの処理中にエラーが発生した場合、クライアント、すなわちリクエストの送信者にそのエラーの内容を通知する必要があります。クライアントは、各種言語を使用して様々なプラットフォーム上に作成できるため、エラーを通知するには、プラットフォームに依存しない標準のメカニズムが必要です。

SOAP仕様(http://www.w3.org/TR/soap/で入手可能)では、SOAPフォルトを使用して、SOAPメッセージにエラーを記述するためのプラットフォームに依存しない標準の方法を定義しています。一般に、SOAPフォルトはアプリケーション例外に類似しています。SOAPフォルトは、ビジネス・ロジック・エラーや予期せぬ状況を報告するために受信側によって生成されます。

JAX-WSでは、Java WebサービスによってスローされるJava例外(java.lang.Exception)がSOAPフォルトにマップされ、フォルトの理由を通知するためにクライアントに返されます。SOAPフォルトのタイプは、次のいずれかになります。

- モデル化: Webサービスのデプロイ時に、Javaコードのビジネス・ロジックから明示的にスローされ、WSDLファイルのwsdl:fault定義にマップされる例外にマップされます。この場合、SOAPフォルトは事前に定義されています。

- 非モデル化: WSDLにビジネス・ロジック・フォルトが定義されていない場合に、実行時に生成される例外(java.lang.RuntimeExceptionなど)にマップされます。この場合、Java例外は汎用的なSOAPフォルト例外であるjavax.xml.ws.soap.SOAPFaultExceptionとして表されます。

フォルトは、リクエスト/レスポンス・メッセージングが使用中の場合にのみ送信者に返されます。Webサービス操作が一方向として構成されている場合、SOAPフォルトは送信者には返されませんが、後続の処理のために格納されます。

図19-1に示すように、JAX-WSはSOAPプロトコル・バインディングでSOAPフォルト処理を行います。SOAPバインディングは、例外をSOAPフォルト・メッセージにマップします。

図19-1 SOAPフォルト処理の仕組み

SOAPフォルト要素のコンテンツ

SOAPメッセージでエラーおよびステータス情報を送信するには、SOAP <Fault>要素を使用します。<Fault>要素は本体要素の子要素です。SOAPメッセージの本体には<Fault>要素を1つだけ含めることができます。

次の項では、SOAP 1.2および1.1のSOAP <Fault>要素のコンテンツを定義します。

- SOAP 1.2 <Fault>要素のコンテンツ

- SOAP 1.1 <Fault>要素のコンテンツ

SOAP 1.2 <Fault>要素のコンテンツ

SOAP 1.2の<Fault>要素には、表19-1に定義されているサブ要素が含まれます。

表19-1 SOAP 1.2 <Fault>要素のサブ要素

要素のサブ要素について説明します。" title="SOAP 1.2 <Fault>要素のサブ要素" width="100%">

サブ要素

説明

必須/省略可能

env:Code

フォルト・エラー・コードに関する情報。env:Code要素は次の2つのサブ要素で構成されます。

- env:Value

- env: Subcode

これらのサブ要素は次のように定義されています。

必須

env:Value

フォルトに関する詳細情報を示すコード値。SOAP仕様で事前に定義されている一連のコード値は次のとおりです。

- VersionMismatch: SOAPエンベロープ要素に無効な名前空間が定義されています。SOAPエンベロープは、http://schemas.xmlsoap.org/soap/envelopeの名前空間に準拠する必要があります。

- MustUnderstand: SOAPヘッダー・エントリが処理側で認識できません。

- Sender: メッセージのフォーマットが正しくないか、情報が欠落しています。

- Receiver: サーバーの問題によりメッセージを処理できません。

- DataEncodingUnknown: 受信したメッセージには、認識できないエンコーディング・スタイルの値が使用されています。SOAPヘッダー・ブロックおよびSOAP本体の子要素に対してエンコーディング・スタイルを定義できます。このエンコーディング・スタイルはWebサービスのサーバーで認識される必要があります。

必須

env:Subcode

フォルトに関する詳細情報を示すサブコード値。このサブ要素は、再帰的構造をとることができます。

省略可能

env:Reason

フォルトに関する判読可能な記述。

<env:Reason>要素には、1つ以上の<Text>要素が含まれており、それぞれの要素にはフォルトに関する情報が異なる言語で格納されます。

必須

env:Node

フォルトを発生させたアクター(SOAPノード)に関する情報。

省略可能

env:Role

フォルトが発生したときにアクターが実行していたロール。

省略可能

env:Detail

アプリケーション固有の情報(スローされた例外など)。

省略可能

次の例では、SOAP 1.2のフォルト・メッセージを示します。

例19-1 SOAP 1.2のフォルト・メッセージの例

<?xml version="1.0"?>
<env:Envelope xmlns:env=http://www.w3.org/2003/05/soap-envelope>
<env:Body>
<env:Fault>
<env:Code>
<env:Value>env:Sender</env:Value>
<env:Subcode>
<env:Value>rpc:BadArguments</env:Value>
</env:Subcode>
</env:Code>
<env:Reason>
<env:Text xml:lang=en-US>Processing error<env:Text>
</env:Reason>
<env:Detail>
<e:myFaultDetails
xmlns:e=http://travelcompany.example.org/faults>
<e:message>Name does not match card number</e:message>
<e:errorcode>999</e:errorcode>
</e:myFaultDetails>
</env:Detail>
</env:Fault>
</env:Body>
</env:Envelope>

SOAP 1.1 <Fault>要素のコンテンツ

SOAP 1.1の<Fault>要素には、表19-2に定義されているサブ要素が含まれます。

表19-2 SOAP 1.1 <Fault>要素のサブ要素

要素のサブ要素について説明します。" title="SOAP 1.1 <Fault>要素のサブ要素" width="100%">

サブ要素

説明

faultcode

フォルトに関する詳細情報を示す標準コード。SOAP仕様で事前に定義されている一連のコード値は次のとおりです。この一連のフォルト・コード値は、アプリケーションで拡張できます。

事前定義済のフォルト・コード値は次のとおりです。

- VersionMismatch: SOAPエンベロープ要素に無効な名前空間が定義されています。SOAPエンベロープは、http://schemas.xmlsoap.org/soap/envelopeの名前空間に準拠する必要があります。

- MustUnderstand: SOAPヘッダー・エントリが処理側で認識できません。

- Client: メッセージのフォーマットが正しくないか、情報が欠落しています。

- Server: サーバーの問題によりメッセージを処理できません。

faultstring

フォルトに関する判読可能な記述。

faultactor

フォルトを発生させたアクター(SOAPノード)に関連付けられているURI。RPCスタイルのメッセージングでは、アクターはWebサービスのURIです。

detail

アプリケーション固有の情報(スローされた例外など)。この要素は、XML構造またはプレーン・テキストにすることができます。

次の例では、SOAP 1.1のフォルト・メッセージを示します。

例19-2 SOAP 1.1のフォルト・メッセージの例

<?xml version="1.0"?>
<soap:Envelope
xmlns:soap='http://schemas.xmlsoap.org/soap/envelope'>
<soap:Body>
<soap:Fault>
<faultcode>soap:VersionMismatch</faultcode>
<faultstring, xml:lang='en">
Message was not SOAP 1.1 compliant
</faultstring>
<faultactor>
http://sample.org.ocm/jws/authnticator
</faultactor>
</soap:Fault>
</soap:Body>
</soap:Envelope>

モデル化されたフォルトの使用

前述したように、モデル化されたフォルトは、Javaコードのビジネス・ロジックから明示的にスローされる例外にマップされます。この場合、その例外は、Webサービスのデプロイ時にWSDLファイルのwsdl:fault定義にマップされます。

次の項では、モデル化されたフォルトの使用に関する詳細を説明します。

- カスタム例外の作成と使用

- モデル化されたフォルトのWSDLファイルにおけるマッピングの仕組み

- SOAPメッセージによるフォルト通知の仕組み

- Webサービス・クライアントの作成

カスタム例外の作成と使用

モデル化されたフォルトを使用するには、カスタムのJava例外を作成して、Webサービス内からスローする必要があります。

例19-3では、Webサービスからスローされるカスタム例外の簡単な例を示します。この例外の名前はMissingNameで、入力引数が空の場合にスローされます。

例19-3 カスタム例外を使用したWebサービス

package examples;
import javax.jws.WebService;

@WebService(name="HelloWorld", serviceName="HelloWorldService")
public class HelloWorld {
public String sayHelloWorld(String message) throws MissingName {
System.out.println("Say Hello World: " + message);
if (message == null || message.isEmpty()) {
throw new MissingName();
}
return "Here is the message: '" + message + "'";
}
}

例19-4に、例外のクラスMissingName.javaを示します。

例19-4 カスタム例外クラス(MissingName)

package examples;
import java.lang.Exception;

public class MissingName extends Exception {
public MissingName() {
super("Your name is required.");
}
}

モデル化されたフォルトのWSDLファイルにおけるマッピングの仕組み

JAX-WSのJava-to-WSDLマッピングにより、java.lang.Exceptionのサブクラスがwsdl:faultメッセージにバインドされます。例19-4は、例19-3のアノテーション付きのWebサービスから生成されたWSDLを示しています。*

この例の内容:

- <message name="MissingName">要素は、MissingNameメッセージのパート、すなわちfaultと、関連付けられたデータ型tns:MissingNameを定義しています。

<message name="MissingName">
<part name="fault" element="tns:MissingName" />
</message>

- MissingName SOAPフォルトは、sayHelloWorld操作にマップされています。

<operation name="sayHelloWorld">
<input message="tns:sayHelloWorld" />
<output message="tns:sayHelloWorldResponse" />
<fault message="tns:MissingName" name="MissingName" />
</operation>

この例の<fault>サブ要素は、sayHelloWorld()メソッド宣言のthrows MissingName句から導出されています(例19-3を参照)。

public String sayHelloWorld(String message) throws MissingName {
...
}

- フォルト・メッセージは、<binding>要素のsayHelloWorld操作にもマップされます。

<fault name="MissingName">
<soap:fault name="MissingName" use="literal" />
</fault>

例19-5 モデル化された例外を使用したWSDLの例

<?xml version="1.0" encoding="UTF-8" ?>
<definitions
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:tns="http://examples/"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns="http://schemas.xmlsoap.org/wsdl/"
targetNamespace="http://examples/"
name="HelloWorldService">
<types>
<xsd:schema>
<xsd:import namespace="http://examples/"
schemaLocation="http://localhost:7001/HelloWorld/HelloWorldService?xsd=1"/>
</xsd:schema>
</types>
<message name="sayHelloWorld">
<part name="parameters" element="tns:sayHelloWorld" />
</message>
<message name="sayHelloWorldResponse">
<part name="parameters" element="tns:sayHelloWorldResponse" />
</message>
<message name="MissingName">
<part name="fault" element="tns:MissingName" />
</message>
<portType name="HelloWorld">
<operation name="sayHelloWorld">
<input message="tns:sayHelloWorld" />
<output message="tns:sayHelloWorldResponse" />
<fault message="tns:MissingName" name="MissingName" />
</operation>
</portType>
<binding name="HelloWorldPortBinding" type="tns:HelloWorld">
<soap:binding transport="http://schemas.xmlsoap.org/soap/http"
style="document" />
<operation name="sayHelloWorld">
<soap:operation soapAction="" />
<input>
<soap:body use="literal" />
</input>
<output>
<soap:body use="literal" />
</output>
<fault name="MissingName">
<soap:fault name="MissingName" use="literal" />
</fault>
</operation>
</binding>
<service name="HelloWorldService">
<port name="HelloWorldPort" binding="tns:HelloWorldPortBinding">
<soap:address
location="http://localhost:7001/HelloWorld/HelloWorldService" />
</port>
</service>

SOAPメッセージによるフォルト通知の仕組み

例19-6は、MissingName Java例外がスローされた場合に、生成されたSOAPメッセージでSOAPフォルトが通知される仕組みを示しています。

例19-6 MissingName例外のSOAPフォルト・メッセージの例

<?xml version = '1.0' encoding = 'UTF-8'?>
<S:Envelope xmlns:S="http://schemas.xmlsoap.org/soap/envelope/">
<S:Body>
<S:Fault xmlns:ns4="http://www.w3.org/2003/05/soap-envelope">
<faultcode>S:Server</faultcode>
<faultstring>Your name is required.</faultstring>
<detail>
<ns2:MissingName xmlns:ns2="http://examples/">
<message>Your name is required.</message>
</ns2:MissingName>
<ns2:exception xmlns:ns2="http://jax-ws.java.net/"
class="examples.MissingName" note="To disable this feature, set
com.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTrace system
property to false">
<message>Your name is required.</message>
<ns2:stackTrace>
<ns2:frame class="examples.HelloWorld" file="HelloWorld.java"
line="14" method="sayHelloWorld"/>
...
</ns2:stackTrace>
</ns2:exception>
</detail>
</S:Fault>
</S:Body>
</S:Envelope>

Webサービス・クライアントの作成

clientgenを使用して、マップされたフォルトを含むWSDLファイルからWebサービス・クライアントを生成すると、必要な例外クラス(マップされた例外、フォルトBean、サービス実装クラス、クライアント実装クラスなど)が自動的に生成されますが、それらの例外クラスは変更する必要があります。次の項では、その手順について説明します。

- 生成されたJava例外クラスの確認

- 生成されたJavaフォルトBeanクラスの確認

- クライアント側のサービス実装の確認

- クライアント実装クラスの作成

clientgenの詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のclientgenに関する項を参照してください。

生成されたJava例外クラスの確認

生成されたJava例外クラスの例を例19-7に示します。@WebFaultアノテーションは、このクラスをマップされた例外として指定しています。

例19-7 生成されたJava例外クラスの例

package examples.client;

import javax.xml.ws.WebFault;

@WebFault(name = "MissingName", targetNamespace = "http://examples/")
public class MissingName_Exception extends Exception {
private MissingName faultInfo;
public MissingName_Exception(String message, MissingName faultInfo) { ... }
public MissingName_Exception(String message, MissingName faultInfo,
Throwable cause) { ... }
public MissingName getFaultInfo() { ... }
}

生成されたJavaフォルトBeanクラスの確認

生成されたJavaフォルトBeanクラスの例を例19-8に示します。このクラスには、フォルト・メッセージのgetterとsetterが定義されています。

例19-8 生成されたJavaフォルトBeanクラスの例

package examples.client;

import javax.xml.bind.annotation.XmlAccessType;
import javax.xml.bind.annotation.XmlAccessorType;
import javax.xml.bind.annotation.XmlType;

@XmlAccessorType(XmlAccessType.FIELD)
@XmlType(name = "MissingName", propOrder = {
"message"
})
public class MissingName {

protected String message;

public String getMessage() {
return message;
}

public void setMessage(String value) {
this.message = value;
}
}

クライアント側のサービス実装の確認

生成されたクライアント側サービス実装クラスの例を例19-9に示します。

例19-9 クライアント側のサービス実装

package examples.client;
...
@WebService(name = "HelloWorld", targetNamespace = "http://examples/")
@XmlSeeAlso({
ObjectFactory.class
})
public interface HelloWorld {

@WebMethod
@WebResult(targetNamespace = "")
@RequestWrapper(localName = "sayHelloWorld",
targetNamespace = "http://examples/",
className = "examples.client.SayHelloWorld")
@ResponseWrapper(localName = "sayHelloWorldResponse",
targetNamespace = "http://examples/",
className = "examples.client.SayHelloWorldResponse")
public String sayHelloWorld(
@WebParam(name = "arg0", targetNamespace = "")
String arg0)
throws MissingName_Exception;
}

クライアント実装クラスの作成

Webサービス・メソッドを呼び出し、カスタム例外をスローするクライアント実装クラスを作成します。続いて、そのクライアントをコンパイルし、実行します。Webサービス・クライアントの作成の詳細は、『Oracle WebLogic Server 12.1.3 JAX-WS Webサービスの開発』のWebサービスの呼出しに関する項を参照してください。

例19-10に、クライアント実装クラスの例を示します。

例19-10 クライアント実装クラス

package examples.client;

import javax.xml.namespace.QName;
import java.net.MalformedURLException;
import java.net.URL;
import examples.client.MissingName_Exception;

public class Main {

public static void main(String[] args) throws MissingName_Exception {
HelloWorldService service;

try {
service = new HelloWorldService(new URL(args[0] + "?WSDL"),
new QName("http://examples/", "HelloWorldService") );
} catch (MalformedURLException murl) { throw new RuntimeException(murl); }
HelloWorld port = service.getHelloWorldPort();

String result = null;
try {
result = port.sayHelloWorld("");
} catch (MissingName_Exception e) {
System.err.println("Error: " + e);
}
System.out.println( "Got result: " + result );
}
}

モデル化されていないフォルトの使用

前述したように、モデル化されていないフォルトは、WSDLにビジネス・ロジック・フォルトが定義されていない場合は、実行時に生成される例外(java.lang.RuntimeExceptionなど)にマップされます。この場合、Java例外は汎用的なSOAPフォルト例外であるjavax.xml.ws.soap.SOAPFaultExceptionとして表されます。

次の例では、モデル化されていないフォルトにマップされた例外を示します。

例19-11 モデル化されていないフォルトを使用したWebサービスの例

package examples;

import javax.jws.WebService;
@WebService(name="HelloWorld", serviceName="HelloWorldService")
public class HelloWorld {
public String sayHelloWorld(String message) throws MissingName {
System.out.println("Say Hello World: " + message);
if (message == null || message.isEmpty()) {
throw new MissingName(); // Modeled fault
} else if (message.equalsIgnoreCase("abc")) {
throw new RuntimeException("Please enter a name."); //Unmodeled fault
}

return "Here is the message: '" + message + "'";
}
}

この例では、文字列「abc」がメソッドに渡されると、次のSOAPFaultExceptionメッセージおよびRuntimeExceptionメッセージが次のようにログ・ファイルに返されます。

例19-12 モデル化されていないフォルトのログ・ファイル・メッセージの例

...
run:
[java] Exception in thread "main" javax.xml.ws.soap.SOAPFaultException: Please
enter a name.
...
Caused by: java.lang.RuntimeException: Please enter a name.\
...

例外処理プロセスのカスタマイズ

SOAPメッセージ・ハンドラを使用して、SOAPフォルトの処理プロセスをカスタマイズできます。SOAPメッセージ・ハンドラは、Webサービスのリクエストとレスポンスの両方でSOAPメッセージをインターセプトするメカニズムです。SOAPメッセージ・ハンドラを作成すると、WebサービスおよびクライアントがSOAPメッセージの追加処理を実行できるようになります。詳細は、第18章「SOAPメッセージ・ハンドラの作成と使用」を参照してください。

SOAPフォルトからのスタック・トレースの無効化

注意:
com.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTraceプロパティは、JDK 6.0の拡張としてサポートされています。このAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

デフォルトでは、スタック・トレース全体(ネスト例外を含む)が、SOAPフォルト・メッセージの詳細に含まれます。たとえば、次の例は、スタック・トレースが含まれるSOAPフォルト・メッセージを示しています。

例19-13 SOAPフォルト・メッセージのスタック・トレースの例

<?xml version = '1.0' encoding = 'UTF-8'?>
<S:Envelope xmlns:S="http://www.w3.org/2003/05/soap-envelope">
<S:Body>
<S:Fault xmlns:ns4="http://schemas.xmlsoap.org/soap/envelope/">
<S:Code>
<S:Value>S:Receiver</S:Value>
</S:Code>
<S:Reason>
<S:Text xml:lang="en">String index out of range: 3</S:Text>
</S:Reason>
<S:Detail>
<ns2:exception xmlns:ns2="http://jax-ws.java.net/"
class="java.lang.StringIndexOutOfBoundsException" note="To disable this feature, set
com.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTrace system property
to false">
<message>String index out of range: 3</message>
<ns2:stackTrace>
<ns2:frame class="java.lang.String" file="String.java" line="1934"
method="substring"/>
<ns2:frame class="ratingservice.CreditRating" file="CreditRating.java"
line="21" method="processRating"/>
<ns2:frame class="sun.reflect.NativeMethodAccessorImpl"
file="NativeMethodAccessorImpl.java" line="native" method="invoke0"/>
<ns2:frame class="sun.reflect.NativeMethodAccessorImpl"
file="NativeMethodAccessorImpl.java" line="39" method="invoke"/>
<ns2:frame class="sun.reflect.DelegatingMethodAccessorImpl"
file="DelegatingMethodAccessorImpl.java" line="25" method="invoke"/>
<ns2:frame class="java.lang.reflect.Method" file="Method.java" line="597"
method="invoke"/>
...
</ns2:stackTrace>
</ns2:exception>
</S:Detail>
</S:Fault>
</S:Body>
</S:Envelope>

Java起動プロパティcom.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTraceをfalseに設定することで、スタック・トレースがSOAPフォルト・メッセージに含まれないようにすることができます。

スタック・トレースを無効にするには:

1. ORACLE_HOME/user_projects/domains/domainName/startWebLogic.cmdファイルで次のエントリを探します。ここで、ORACLE_HOMEは、Oracle WebLogic ServerをインストールしたときにOracleホームとして指定したディレクトリです。

set JAVA_OPTIONS=%SAVE_JAVA_OPTIONS%

2. エントリを次のように編集します。

set JAVA_OPTIONS=-Dcom.sun.xml.ws.fault.SOAPFaultBuilder.disableCaptureStackTrace=false %SAVE_JAVA_OPTIONS%

3. startWebLogic.cmdファイルを保存します。

その他の例外

Webサービスで明示的にスローされるカスタム例外、およびビジネス・ロジックでキャッチされない例外のマッピングに使用されるSOAPFaultExceptionsに加えて、この他に2つの例外があります。これらの例外は、Webサービス・クライアントに通知される可能性があるため、確認しておく必要があります。

表19-3 その他の例外

例外

説明

javax.xml.ws.WebServiceException

すべてのJAX-WS APIランタイム例外の基本例外。JAX-WS Javaクラス(Service.BindingProvider、Dispatchなど)の呼出しに失敗した場合に使用されます。

java.util.concurrent.ExecutionException

クライアントが非同期呼出しからレスポンスを取得する際に、JAX-WS非同期呼出しで使用されます。

20 バイナリ・データ転送の最適化

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの転送を最適化するために、SOAPメッセージを添付ファイルとして送信する方法について説明します。

この章の内容は次のとおりです:

- MTOM/XOPを使用したバイナリ・データ転送の最適化

- SOAP添付ファイルのストリーミング

- swaRefを使用した添付ファイル付きSOAPメッセージの送信

MTOM/XOPを使用したバイナリ・データ転送の最適化

SOAP MTOM/XOP (Message Transmission Optimization Mechanism/XML-binary Optimized Packaging)では、SOAPメッセージ内のxs:base64Binary型またはxs:hexBinary型のXMLデータの転送を最適化する方法が定義されています。トランスポート・プロトコルがHTTPの場合、Multipurpose Internet Mail Extension (MIME)添付ファイルを使用して、送信側と受信側の両方に対して同時にSOAPメッセージ内のXMLデータへの直接アクセスを許可する間にデータを伝達します。このとき、base64BinaryまたはhexBinaryデータのマーシャリングにMIMEアーティファクトが使用されていたことを意識する必要はありません。

バイナリ・データ最適化プロセスの手順は次のとおりです:

1. バイナリ・データのエンコード

2. SOAPエンベロープからのバイナリ・データの削除

3. バイナリ・データの圧縮

4. MIMEパッケージへのバイナリ・データの添付

5. SOAPエンベロープ内のMIMEパッケージへの参照の追加

MTOM/XOPのサポートは、JWSアノテーションの使用によって、JAX-WSでは標準となっています。MTOM仕様では、MTOMが有効化されている場合に、base64binaryまたはhexBinaryデータの送信時にWebサービスのランタイムでXOPバイナリ最適化を使用することは必須ではありません。むしろ、この仕様では、ランタイムがこれを選択して行うようになっています。これは場合によっては、直接SOAPメッセージ内にバイナリ・データを送信するほうが、より効率的であるとランタイムで判断されることがあるためです。一例としては、トランスポートされるデータ量が少なく、単にデータをそのままインライン処理するよりも多くのリソースが、会話およびトランスポートのオーバーヘッドにより消費されてしまう場合が挙げられます。

デフォルトでbase64Binary XMLデータ型にマップされるJavaタイプは、javax.activation.DataHandler、java.awt.Imageとjavax.xml.transform.Sourceです。base64BinaryまたはhexBinary型の要素は、デフォルトでbyte[]にマップされます。

次の表に、MTOM/XOPを使用してbase64BinaryまたはhexBinary型の添付ファイルを送信する手順をまとめます。

表20-1 MTOM/XOPを使用してバイナリ・データを送信する手順

#

手順

説明

1

MTOM添付ファイルとして使用する予定のデータ型のアノテーションを追加します。(オプション)

使用するプログラミング・モデルに応じ、JavaクラスまたはWSDLにアノテーションを追加して、バイナリ・データの送信に使用するコンテンツ・タイプを定義できます。この手順はオプションです。XMLバイナリ型は、デフォルトではJava byte[]にマップされます。詳細については、「データ型のアノテーションの追加」を参照してください。

2

WebサービスでMTOMを有効にします。

「WebサービスでMTOMの有効化」を参照してください。

3

WebサービスのクライアントでMTOMを有効にします。

「クライアントでMTOMの有効化」を参照してください。

4

添付ファイルのしきい値の設定

xs:binary64データをインラインまたは添付ファイルとして送信する場合に指定する添付ファイルのしきい値を設定します。「添付ファイルのしきい値の設定」を参照してください。

5

(オプション) HTTPチャンクを有効にします。

HTTPチャンクを有効にして、MTOM添付ファイルの処理の際、クライアント側の過度のバッファリングを最小限に抑えます。「HTTPチャンクの有効化」を参照してください。

詳細は、次を参照してください。

- MTOMの仕様(http://www.w3.org/TR/soap12-mtom)

- XOPの仕様(http://www.w3.org/TR/xop10)

データ型のアノテーションの追加

使用するプログラミング・モデルに応じ、JavaクラスまたはWSDLにアノテーションを追加して、バイナリ・データの送信に使用するMIMEコンテンツ・タイプを定義できます。この手順はオプションです。

次の表に、MIMEコンテンツ・タイプとJavaタイプのマッピングを定義します。型によっては、デフォルトのマッピングが存在します。デフォルトのマッピングが存在しないMIMEコンテンツ・タイプは、DataHandlerにマップされます。

表20-2 MIMEコンテンツ・タイプとJava型のマッピング

MIMEコンテンツ・タイプ

Java型

image/gif

java.awt.Image

image/jpeg

java.awt.Image

text/plain

java.lang.String

text/xml or application/xml

javax.xml.transform.Source

*/*

javax.activation.DataHandler

以下の節では、データ型のアノテーションを追加する方法について説明します。Javaから始める方法と、WSDLから始める方法があります。

- データ型のアノテーションを追加する: Javaから始める場合

- データ型のアノテーションを追加する: WSDLから始める場合

データ型のアノテーションを追加する: Javaから始める場合

バイナリ・データの送信に使用するコンテンツ・タイプの定義をJavaから始める場合は、バイナリ・データを保持するフィールドに@XmlMimeTypeアノテーションを追加します。

バイナリ・データを保持するフィールドは、DataHandler型にする必要があります。

次のサンプルに、バイナリ・データを保持するJavaクラス内のフィールドにアノテーションを追加する方法を示します。

@WebMethod
@Oneway
public void dataUpload(
@XmlMimeType("application/octet-stream") DataHandler data)
{
}

データ型のアノテーションを追加する: WSDLから始める場合

バイナリ・データの送信に使用するコンテンツ・タイプの定義をWSDLから始める場合は、以下のいずれかの属性を使用して、xs:base64Binaryまたはxs:hexBinary型のWSDL要素にアノテーションを追加します。

- xmime:contentType - この要素のコンテンツ・タイプを定義します。

- xmime:expectedContentType - バイナリ・データとして容認するメディア・タイプの範囲を定義します。

次のサンプルでは、base64binary型のimage要素を、java.awt.Image Javaタイプにマップされるimage/gif MIMEタイプにマップしています。

<element name="image" type="base64Binary"
xmime:expectedContentTypes="image/gif"
xmlns:xmime="http://www.w3.org/2005/05/xmlmime"/>

WebサービスでMTOMの有効化

次の項で説明しているように、アノテーションまたはWS-Policyファイルを使用してWebサービスでMTOMを有効にすることができます。

- アノテーションを使用してWebサービスでMTOMの有効化

- WS-PolicyファイルをアタッチしてWebサービスでMTOMの有効化

アノテーションを使用してWebサービスでMTOMの有効化

WebサービスでMTOMを有効にするには、次のサンプルのようにサービス・エンドポイント実装クラスに@java.xml.ws.soap.MTOMアノテーションを指定します。関連するコードは太字で示されています。

package examples.webservices.mtom;

import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.xml.ws.soap.MTOM;

@MTOM
@WebService(name="MtomPortType",
serviceName="MtomService",
targetNamespace="http://example.org")
public class MTOMImpl {
@WebMethod
public String echoBinaryAsString(byte[] bytes) {
return new String(bytes);

}
}

WS-PolicyファイルをアタッチしてWebサービスでMTOMの有効化

前の項で説明したように、@MTOMアノテーションに加えて、WebLogic JAX-WS WebサービスでのMTOM/XOPのサポートはあらかじめパッケージ化されたWS-PolicyファイルMtom.xmlを使用して実装されます。WS-Policyファイルは、http://www.w3.org/TR/ws-policyで説明されているWS-Policy仕様に準拠しています。この仕様では、WEBサービスのポリシー(この場合は、バイナリ・データ送信のためのMTOM/XOPの使用)を記述および通信する汎用モデルおよびXML構文を提供しています。WebサービスWSDLのtypesセクションへの、あらかじめパッケージ化されたMtom.xml WS-Policyファイルのインストールは、次のようになります(参考のためにのみ掲載しています。このファイルは変更できません)。

<wsp:Policy wsu:Id="myService_policy">
<wsp:ExactlyOne>
<wsp:All>
<wsoma:OptimizedMimeSerialization
xmlns:wsoma="http://schemas.xmlsoap.org/ws/2004/09/policy/optimizedmimeserialization" />
</wsp:All>
</wsp:ExactlyOne>
</wsp:Policy>

コンパイルされたJWSファイルをWebLogic Serverにデプロイする際には、MTOM WS-Policyファイルを参照する次のスニペットが動的WSDL内に自動的に含まれます。このスニペットは、WebサービスがMTOM/XOPを使用することを示しています。

<wsdl:binding name="BasicHttpBinding_IMtomTest"
type="i0:IMtomTest">
<wsp:PolicyReference URI="#myService_policy" />
<soap:binding transport="http://schemas.xmlsoap.org/soap/http" />

JWSファイルで@Policyメタデータ・アノテーションを指定することによって、開発時にWebサービスとMtom.xml WS-Policyファイルを関連付けることができます。動的WSDLに、必須であるMtom.xmlファイルへの参照が確実に含まれるよう、必ずattachToWsdl=true属性も指定します。下記の例を参照してください。

デプロイメント時にWebサービスとMtom.xml WS-Policyファイルを関連付けるには、デプロイメント直前にtypesセクションにポリシーを追加し、WSDLを修正します。

また、WebLogic Server管理コンソールを使用して実行時にファイルをアタッチできます。詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWS-PolicyファイルのWebサービスへのアタッチに関する項を参照してください。この節では、JWSアノテーションの使用方法について説明します。

次の簡単なJWSファイルの例では、JWSファイルで@weblogic.jws.Policyアノテーションを使用して、あらかじめパッケージ化されたMtom.xmlファイルをWebサービスに適用することを指定する方法を示します(該当するコードは太字で示してあります)。

package examples.webservices.mtom;
import javax.jws.WebMethod;
import javax.jws.WebService;
import weblogic.jws.Policy;
@WebService(name="MtomPortType",
serviceName="MtomService",
targetNamespace="http://example.org")
@Policy(uri="policy:Mtom.xml", attachToWsdl=true)
public class MtomImpl {
@WebMethod
public String echoBinaryAsString(byte[] bytes) {
return new String(bytes);
}

クライアントでMTOMの有効化

WebサービスのクライアントでMTOMを有効にするには、次のサンプルのように、Webサービスのプロキシまたはディスパッチの作成時にパラメータとしてjavax.xml.ws.soap.MTOMFeatureのインスタンスを渡します。関連するコードは太字で示されています。

package examples.webservices.mtom.client;

import javax.xml.ws.soap.MTOMFeature;

public class Main {
public static void main(String[] args) {
String FOO = "FOO";
MtomService service = new MtomService()
MtomPortType port = service.getMtomPortTypePort(new MTOMFeature());
String result = null;
result = port.echoBinaryAsString(FOO.getBytes());
System.out.println( "Got result: " + result );
}
}

添付ファイルのしきい値の設定

xs:binary64データをインラインまたは添付ファイルとして送信する場合に指定する添付ファイルのしきい値を設定できます。デフォルトの添付ファイルのしきい値は0バイトです。すべてのxs:binary64データは添付ファイルとして送信されます。

添付ファイルのしきい値を設定する方法は以下のとおりです。

- Webサービスで、threshold属性を@java.xml.ws.soap.MTOMアノテーションに渡します。例:

@MTOM(threshold=3072)

- Webサービスのクライアントで、しきい値をjavax.xml.ws.soap.MTOMFeatureに渡します。例:

MtomPortType port = service.getMtomPortTypePort(new MTOMFeature(3072));

上のどちらの例でも、メッセージが3KB以上だと添付ファイルとして送信されます。それ以外の場合、コンテンツはSOAPメッセージ本文の一部としてインラインで送信されます。

HTTPチャンクの有効化

次のいずれかの方法を使用して、トランスポート層でHTTPチャンクを有効にすることにより、MTOM添付ファイルの処理の際、クライアント側の過度のバッファリングを最小限に抑えられます。

- jaxws.transport.streamingシステム・プロパティをtrueに設定する。この場合、コードの変更は不要です。

- プロトコル・バインディング・リクエストのコンテキストで、com.sun.xml.ws.developer.JAXWSProperties.HTTP_CLIENT_STREAMING_CHUNK_SIZEプロパティを設定する。詳細は、http://jax-ws.java.net/nonav/jax-ws-20-fcs/arch/com/sun/xml/ws/developer/JAXWSProperties.htmlにあるJAXWSProperties Javadocを参照してください。

クライアントとしてWebサービスの対話に参加し、大きなメッセージを送信するWebLogic Serverインスタンスで実行されている、CPUに負担のかかるアプリケーションでは、HTTPチャンクを有効にすることをお薦めします。

次のAntビルド・スクリプトの抜粋は、clients.InvokeMTOMServiceというクライアント・アプリケーションを呼び出す場合のシステム・プロパティの設定例を示します。

<target name="run-client">
<java fork="true"
classname="clients.InvokeMTOMService"
failonerror="true">
<classpath refid="client.class.path"/>
<arg line="${http-endpoint}"/>
<jvmarg line=
"-Djaxws.transport.streaming=true"
/>
</java>
</target>

次のコードの抜粋は、HTTP_CLIENT_STREAMING_CHUNK_SIZEプロパティの設定方法を示します。

package examples.webservices.mtomstreaming.client;

import java.util.Map;
import javax.xml.ws.BindingProvider;
import com.sun.xml.ws.developer.JAXWSProperties;
...

public class Main {
public static void main(String[] args) {
...
Map<String, Object> ctxt=((BindingProvider)port).getRequestContext();
ctxt.put(JAXWSProperties.HTTP_CLIENT_STREAMING_CHUNK_SIZE, 8192);
...
}

SOAP添付ファイルのストリーミング

注意:
com.sun.xml.ws.developer.StreamingDataHandler APIは、JAX-WS RIの拡張としてサポートされています。このAPIはWebLogicソフトウェアの一部としては提供されないため、変更される可能性があります。

MTOMと、javax.activation.DataHandlerおよびcom.sun.xml.ws.developer.StreamingDataHandler APIを使用すると、添付ファイルを含むインバウンドSOAPメッセージを読み取る際に、デフォルト動作としてメッセージ全体をメモリーに読み込むかわりに、WebサービスでストリーミングAPIを使用することを指定できます。この機能を使用すると、SOAPメッセージが非常に大きいWebサービスのパフォーマンスを向上させることができます。

注意:
ストリームMTOMはメッセージの暗号化と組み合せて使用できません。

以降の節では、クライアント側およびサーバー側でSOAP添付ファイルのストリーミングを使用する方法について説明します。

クライアント側のサンプル

次のサンプルでは、クライアント側でSOAP添付ファイルのストリーミングを使用する方法を示します。

package examples.webservices.mtomstreaming.client;

import java.util.Map;
import java.io.InputStream;
import javax.xml.ws.soap.MTOMFeature;
import javax.activation.DataHandler;
import javax.xml.ws.BindingProvider;
import com.sun.xml.ws.developer.JAXWSProperties;
import com.sun.xml.ws.developer.StreamingDataHandler;

public class Main {
public static void main(String[] args) {
MtomStreamingService service = new MtomStreamingService();
MTOMFeature feature = new MTOMFeature();
MtomStreamingPortType port = service.getMtomStreamingPortTypePort(
feature);
Map<String, Object> ctxt=((BindingProvider)port).getRequestContext();
ctxt.put(JAXWSProperties.HTTP_CLIENT_STREAMING_CHUNK_SIZE, 8192);
DataHandler dh = new DataHandler(new
FileDataSource("/tmp/example.jar"));
port.fileUpload("/tmp/tmp.jar",dh);

DataHandler dhn = port.fileDownload("/tmp/tmp.jar");
StreamingDataHandler sdh = (StreamingDataHandler)dhn;
try{
File file = new File("/tmp/tmp.jar");
sdh.moveTo(file);
sdh.close();
}
catch(Exception e){
e.printStackTrace();
}
}
}

このサンプルでは以下を行っています。

- WebサービスのクライアントでMTOMを有効にし、Webサービスのプロキシまたはディスパッチの作成時にパラメータとしてjavax.xml.ws.soap.MTOMFeatureのインスタンスを渡します。

- MTOMストリーミング・クライアントでのHTTPチャンクを有効にすることで、HTTPストリーミングのサポートを構成します。詳細は、「HTTPチャンクの有効化」を参照してください。

Map<String, Object> ctxt = ((BindingProvider)port).getRequestContext();
ctxt.put(JAXWSProperties.HTTP_CLIENT_STREAMING_CHUNK_SIZE, 8192);

- port.fileUploadメソッドを呼び出します。

- DataHandlerをStreamingDataHandlerにキャストし、StreamingDataHandler.readOnce()メソッドを使用して添付ファイルを読み込みます。

サーバー側のサンプル

次のサンプルでは、サーバー側でSOAP添付ファイルのストリーミングを使用する方法を示します。

package examples.webservices.mtomstreaming;

import java.io.File;
import java.jws.Oneway;
import javax.jws.WebMethod;
import java.io.InputStream;
import javax.jws.WebService;
import javax.xml.bind.annotation.XmlMimeType;
import javax.xml.ws.WebServiceException;
import javax.xml.ws.soap.MTOM;
import javax.activation.DataHandler;
import javax.activation.FileDataSource;
import com.sun.xml.ws.developer.StreamingAttachment;
import com.sun.xml.ws.developer.StreamingDataHandler;

@StreamingAttachment(parseEagerly=true, memoryThreshold=40000L)
@MTOM
@WebService(name="MtomStreaming",
serviceName="MtomStreamingService",
targetNamespace="http://example.org",
wsdlLocation="StreamingImplService.wsdl")
@Oneway
@WebMethod
public class StreamingImpl {

// Use @XmlMimeType to map to DataHandler on the client side
public void fileUpload(String fileName,
@XmlMimeType("application/octet-stream")
DataHandler data) {
try {
StreamingDataHandler dh = (StreamingDataHandler) data;
File file = new File(fileName);
dh.moveTo(file);
dh.close();
} catch (Exception e) {
throw new WebServiceException(e);
}

@XmlMimeType("application/octet-stream")
@WebMethod
public DataHandler fileDownload(String filename)
{
return  new DataHandler(new FileDataSource(filename));
}
}

このサンプルでは以下を行っています。

- ストリームSOAP添付ファイルを構成するには、@StreamingAttachementアノテーションを使用します。詳細については、「SOAP添付ファイルのストリーミングの構成」を参照してください。

- DataHandlerをマップするため、@XmlMimeTypeアノテーションを以下のように使用します。

- WSDLから始める場合は、生成されたSEIでxmime:expectedContentTypes="application/octet-stream"をDataHandlerにマップするために使用します。

- Javaから始める場合は、生成されたWSDLで適切なスキーマ・タイプを生成するために使用します。

- DataHandlerをStreamingDataHandlerにキャストし、StreamingDataHandler.moveTo(File)メソッドを使用して添付されたコンテンツをファイルに格納します。

SOAP添付ファイルのストリーミングの構成

クライアント側およびサーバー側でのSOAP添付ファイルのストリーミングは、以下を指定することで構成できます。

- 大きな添付ファイルを格納するディレクトリ。

- ストリーミング添付ファイルを徹底的に解析するかどうか。

- メモリーに格納できる添付ファイルの最大サイズ(バイト)。添付ファイルのサイズが指定したバイト数を超える場合はファイルに書き込まれます。

サーバーでSOAP添付ファイルのストリーミングの構成

注意:
com.sun.xml.ws.developer.StreamingAttachment APIは、JDK 6.0の拡張としてサポートされています。このAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

サーバーでSOAP添付ファイルのストリーミングを構成するには、エンドポイント実装で@StreamingAttachmentアノテーションを追加します。次のサンプルでは、ストリーミング添付ファイルを徹底的に解析すること(完全な添付ファイルの読取りまたは書込み)を指定し、メモリーのしきい値を4MBに設定しています。4MB以下の添付ファイルはメモリーに格納されます。

...
import com.sun.xml.ws.developer.StreamingAttachment;
import javax.jws.WebService;

@StreamingAttachment(parseEagerly=true, memoryThreshold=4000000L)
@WebService(name="HelloWorldPortType", serviceName="HelloWorldService")
public class StreamingImpl {
}

クライアントでのSOAP添付ファイルのストリーミングの構成

注意:
com.sun.xml.ws.developer.StreamingAttachmentFeature APIは、JDK 6.0の拡張としてサポートされています。このAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

クライアントでSOAP添付ファイルのストリーミングを構成するには、StreamingAttachmentFeatureオブジェクトを作成し、PortTypeスタブ実装の作成時に引数として渡します。次のサンプルでは、大きなファイルを格納するディレクトリを/tmpに設定し、ストリーミング添付ファイルを徹底的に解析することを指定した上で、メモリーのしきい値を4MBに設定しています。4MB以下の添付ファイルはメモリーに格納されます。

...
import com.sun.xml.ws.developer.StreamingAttachmentFeature;
...
MTOMFeature mtom = new MTOMFeature();
StreamingAttachmentFeature stf = new StreamingAttachmentFeature("/tmp", true, 4000000L);
MtomStreamingService service = new MtomStreamingService();
MtomStreamingPortType port = service.getMtomStreamingPortTypePort(
mtom, stf);
...

swaRefを使用した添付ファイル付きSOAPメッセージの送信

また、表20-3の仕様は、swaRef XML添付型を使用して添付ファイル付きSOAPメッセージを送信するメカニズムを定義しています。

表20-3 添付ファイル付きSOAPメッセージの送信でサポートされる仕様

仕様

説明

SOAP With Attachments (SwA)

添付ファイルをSOAPメッセージでパッケージ化するためのMIME multipart/related構造を定義します。詳細は、http://www.w3.org/TR/SOAP-attachmentsを参照してください。

WS-I Attachments Profile

添付ファイルへの参照をコンテンツID (CID)のURLとして表すためにWSDL記述で使用可能なswaRefスキーマ・タイプを定義します。WS-Iは、swaRef型を定義するパブリック・スキーマを公開しています。このパブリック・スキーマの定義はhttp://ws-i.org/profiles/basic/1.1/xsd/swaref.xsdのXSDを参照してください。

JAXBは、swaRefスキーマ・タイプをjavax.activation.DataHandlerにマップします。

詳細は、http://www.ws-i.org/Profiles/AttachmentsProfile-1.0-2004-08-24.htmlを参照してください。

次の例では、WSDLファイルでswaRefを使用して、claimFormリクエスト・メッセージおよびレスポンス・メッセージが添付ファイルとして渡されるように指定する方法を示します。

例20-1 swaRefデータ型を使用したWSDLファイルの例

<?xml version="1.0" encoding="utf-8"?>
<wsdl:definitions name="SOAPBuilders-mime-cr-test"
xmlns:types="http://example.org/mime/data"
xmlns:xsd="http://www.w3.org/2001/XMLSchema"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:wsdl="http://schemas.xmlsoap.org/wsdl/"
xmlns:tns="http://example.org/mime"
xmlns:mime="http://schemas.xmlsoap.org/wsdl/mime/"
targetNamespace="http://example.org/mime">

<wsdl:types>
<schema
xmlns="http://www.w3.org/2001/XMLSchema"
targetNamespace="http://example.org/mime/data"
xmlns:xmime="http://www.w3.org/2005/05/xmlmime"
elementFormDefault="qualified"
xmlns:ref="http://ws-i.org/profiles/basic/1.1/xsd">
<import namespace="http://ws-i.org/profiles/basic/1.1/xsd"
schemaLocation="WS-ISwA.xsd"/>
. . .
<complexType name="claimFormTypeRequest">
<sequence>
<element name="request" type="ref:swaRef"/>
</sequence>
</complexType>
<complexType name="claimFormTypeResponse">
<sequence>
<element name="response" type="ref:swaRef"/>
</sequence>
</complexType>

<element name="claimFormRequest"  type="types:claimFormTypeRequest"/>
<element name="claimFormResponse" type="types:claimFormTypeResponse"/>
</schema>

</wsdl:types>
. . .
<wsdl:message name="claimFormIn">
<wsdl:part name="data" element="types:claimFormRequest"/>
</wsdl:message>

<wsdl:message name="claimFormOut">
<wsdl:part name="data" element="types:claimFormResponse"/>
</wsdl:message>
. . .
<wsdl:portType name="Hello">
. . .
<wsdl:operation name="claimForm">
<wsdl:input message="tns:claimFormIn"/>
<wsdl:output message="tns:claimFormOut"/>
</wsdl:operation>
</wsdl:portType>
. . .
</wsdl:definitions>

例20-1のWSDLの例で指定したように、swaRef型としてタグ付けされたXMLコンテンツはMIME添付ファイルとして送信され、例20-2に示すように、SOAP本体内の要素でこの添付ファイルへの参照が保持されます。

例20-2 MIME添付ファイル付きSOAPメッセージの例

Content-Type: Multipart/Related; start-info="text/xml"; type="application/xop+xml";
boundary="----=_Part_4_32542424.1118953563492"Content-Length: 1193SOAPAction: ""
------=_Part_5_32550604.1118953563502Content-Type: application/xop+xml; type="text/xml"; charset=utf-8
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
<request xmlns="http://example.org/mtom/data">
cid:b0a597fd-5ef7-4f0c-9d85-6666239f1d25@example.jaxws.sun.com
</request>
</soapenv:Body>
</soapenv:Envelope>
------=_Part_5_32550604.1118953563502
Content-Type: application/xmlContent-ID:
<b0a597fd-5ef7-4f0c-9d85-6666239f1d25@example.jaxws.sun.com>
<?xml
version="1.0" encoding="UTF-8"?><application xmlns="http://java.sun.com/xml/ns/j2ee"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocaption="http://java.sun.com/xml/ns/j2ee
http://java.sun.com/xml/ns/j2ee/application_1_4.xsd" version="1.4">
<display-name>Simple example of application</display-name>
<description>Simple example</description>
<module>
<ejb>ejb1.jar</ejb>
</module>
<module>
<ejb>ejb2.jar</ejb>
</module>
<module>
<web> <web-uri>web.war</web-uri> <context-root>web</context-root></web>
</module></application>

例20-3は、claimForm操作を定義するWebサービスのサンプルを示します。WSDLに定義されているように、リクエスト・メッセージおよびレスポンス・メッセージは、MIME添付ファイルとして送信されます。

例20-3 Webサービスの例

package mime.server;

import javax.jws.WebService;
import javax.xml.ws.Holder;
import javax.xml.transform.Source;
import javax.xml.transform.stream.StreamSource;
import javax.activation.DataHandler;
import java.awt.*;
import java.io.ByteArrayInputStream;

@WebService (endpointInterface = "mime.server.Hello")
public class HelloImpl {
...
public ClaimFormTypeResponse claimForm(ClaimFormTypeRequest data){
ClaimFormTypeResponse resp = new ClaimFormTypeResponse();
resp.setResponse(data.getRequest());
return resp;
}
...
}

例20-4では、claimForm操作を呼び出すWebサービス・クライアントのサンプルを示します。添付ファイルとして転送されるクライアント・リクエスト・データは、DataHandlerデータ型にマップされます。

例20-4 MIME添付ファイルを使用したWebサービス・クライアントの例

package mime.client;

import javax.xml.transform.stream.StreamSource;
import javax.xml.transform.Source;
import javax.activation.DataHandler;
import java.io.ByteArrayInputStream;
import java.awt.*;

public class MimeApp {
public static void main (String[] args){
try {
Object port = new HelloService().getHelloPort ();
testSwaref ((Hello)port);
} catch (Exception ex) {
ex.printStackTrace ();
}
}

private static void testSwaref (Hello port) throws Exception{
DataHandler claimForm = new DataHandler (new StreamSource(
new ByteArrayInputStream(sampleXML.getBytes())), "text/xml");
ClaimFormTypeRequest req = new ClaimFormTypeRequest();
req.setRequest(claimForm);
ClaimFormTypeResponse resp = port.claimForm (req);
DataHandler out = resp.getResponse();
...
}

private static final String sampleXML = "<?xml version=\"1.0\" encoding=\"UTF-8\" ?> \n" +
"<NMEAstd>\n" +
"<DevIdSentenceId>$GPRMC</DevIdSentenceId>\n" +
"<Time>212949</Time>\n" +
"<Navigation>A</Navigation>\n" +
"<NorthOrSouth>4915.61N</NorthOrSouth>\n" +
"<WestOrEast>12310.55W</WestOrEast>\n" +
"<SpeedOnGround>000.0</SpeedOnGround>\n" +
"<Course>360.0</Course>\n" +
"<Date>030904</Date>\n" +
"<MagneticVariation>020.3</MagneticVariation>\n" +
"<MagneticPoleEastOrWest>E</MagneticPoleEastOrWest>\n" +
"<ChecksumInHex>*6B</ChecksumInHex>\n" +
"</NMEAstd>";
}

21 Webサービス永続性の管理

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの永続性を管理する方法について説明します。

この章の内容は次のとおりです:

- Webサービス永続性の概要

- Webサービス永続性を構成するためのロードマップ

- Webサービス永続性の構成

- クラスタでのWebサービス永続性の使用

- Webサービス永続性のクリーンアップ

Webサービス永続性の概要

WebLogic Serverには、Webサービスに組込みの高パフォーマンスのストレージ・ソリューションを提供するデフォルトのWebサービス永続性が用意されています。Webサービス永続性は、長時間実行されるリクエストをサポートし、サーバーの再起動があっても存続するように、次の高度な機能で使用されます。

- 非同期クライアント・トランスポートまたは接続作成を使用したWebサービスの非同期呼出し

- Webサービスの信頼性のあるメッセージング

- メッセージ・バッファリング

- WS-SecureConversationを使用したセキュリティ

具体的には、Webサービス永続性は次の種類の情報を保存するために使用されます。

- クライアントのIDとプロパティ

- ヘッダーと本体を含むSOAPメッセージ

- Webサービスまたはクライアントでメッセージを処理するために必要なコンテキスト・プロパティ(非同期メッセージと同期メッセージの両方)

次の図では、Webサービス永続性の構成例を示します。

図21-1 Webサービス永続性の構成例

次の表では、前の図で示したWebサービス永続性のコンポーネントについて説明します。

表21-1 Webサービス永続性のコンポーネント

コンポーネント

説明

論理ストア

構成要件を提供し、Webサービスを物理ストアとバッファリング・キューに接続します。

物理ストア

物理ストレージ(ファイルやDBMSなど)のデータを保存および取得するためのI/O操作を処理します。物理ストアとしては、WebLogic Server管理コンソールまたはWLSTを使用して構成されたWebLogic Server永続ストアまたはインメモリー・ストアを使用できます。

注意: WebLogic Server永続ストアを論理ストア用の物理ストアとして使用する場合、リクエストとレスポンスのバッファリング・キューの名前は、バッファリングの構成ではなく、論理ストアの構成から取得されます。

バッファリング・キュー

Webサービスのバッファリングされたリクエストとレスポンスを格納します。

Webサービス永続性を構成するときは、次のものを関連付けます。

- 論理ストアとバッファリング・キュー。

- JMS構成を介して物理ストアと関連付けられたバッファリング・キュー。

論理ストアとバッファリング・キューの間の関連付けを使用して、論理ストアと物理ストアの間の関連付けが推論されます。デフォルトの論理ストアは、WseeStoreという名前で、WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を使用してドメインが作成されるときに自動的に作成されます。デフォルトで、サーバー用に構成された物理ストアは、バッファリング・キューと関連付けられます。これにより、すべてのWebサービス永続性とバッファリングで同じ物理ストアが使用されることが保証されます。単一の物理ストアを使用することで、いっそう効率的な単一フェーズのXAトランザクションが保証され、移行が容易になります。

アプリケーション環境内で使用するための1つ以上の論理ストアを構成できます。表21-1では、サーバーServer1とServer2は同じ論理ストアを使用しています。この構成により、クラスタ内で実行するアプリケーションを、単一のストア名にアクセスするようにグローバルに構成できます。後の「Webサービス永続性の構成」で説明するように、Webサービス永続性を様々なレベルで構成して、きめ細かく管理できます。ベスト・プラクティスは「Webサービス永続性を構成するためのロードマップ」で説明します。

Webサービス永続性を構成するためのロードマップ

表21-2では、Webサービス永続性を構成してWebサービスの信頼性のあるメッセージングをサポートするためのベスト・プラクティスについて説明します。

表21-2 Webサービス永続性を構成するためのロードマップ

ベスト・プラクティス

説明

各管理単位(ビジネス単位、部門など)に対する論理ストアを定義します。

異なる論理ストアを定義することで、管理単位ごとのサービスレベル契約をより適切に管理できます。詳細は、「論理ストアの構成」を参照してください。

管理単位に関連する個々のクライアントまたはサービスに対して正しい論理ストアを使用します。

論理ストアは、WebLogic Server、Webサービス、Webサービス・クライアントのいずれかのレベルで構成できます。詳細は、「Webサービス永続性の構成」を参照してください。

論理ストアごとに異なる物理ストアとバッファリング・キューを定義します。

詳細は、「Webサービス永続性の構成の例」を参照してください。

表21-2で定義されているベスト・プラクティスは、保守、障害リカバリ、リソースの移行を容易にします。

たとえば、会社Xが、製造、買掛、売掛などの複数の部門に対するWebサービスを開発しているものとします。ベスト・プラクティスに従うと、会社Xは部門ごとに少なくとも3つの論理ストアを定義します。

さらに、製造部門とIT部門の間には、数分以下のシステム停止を許容できることを指定するサービスレベル契約があるものとします。一方、売掛部門と買掛部門にはさらに緩いサービスレベル契約があり、1時間までのシステム停止は許容されます。Webサービスをホストするシステムと製造部門用のクライアントが使用できなくなった場合、IT部門は、障害から数分以内にこれらのWebサービスとクライアントで必要なリソースを新しいアクティブ・サーバーに移行する必要があります。個別の論理ストアが定義されているため、IT部門は、売掛部門と買掛部門に必要なリソースとは独立して、開発部門の論理ストアと関連付けられているファイル・ストアやJMSサーバーなどを移行できます。

Webサービス永続性の構成

次の表では、Webサービス永続性の各コンポーネントに対して構成できる情報を説明します。

表21-3 Webサービス永続性のコンポーネントの構成の説明

コンポーネント

構成要件の説明

論理ストア

各論理ストアに対して次の情報を構成します。

- 論理ストアの名前。

- ストア内のオブジェクトの最大存続期間。

- ストアから失効したオブジェクトを削除するクリーナ・スレッド。詳細は、「Webサービス永続性のクリーンアップ」を参照してください。

- ネットワーク内の他のサーバーからのアクセス性。

- リクエストとレスポンスのバッファリング・キュー。リクエスト・バッファリング・キューは、関連付けによって物理ストアを類推するために使用されます。

物理ストア

物理ストアに対して次の情報を構成します。

- 物理ストアの名前。

- 種類およびパフォーマンス・パラメータ。

- ストアの場所。

注意: 物理ストアとバッファリング・キューは、両方ではなく、どちらか一方のみを構成します。バッファリング・キューを構成すると、物理ストアの情報は類推されます。

バッファリング・キュー

バッファリング・キューに対して次の情報を構成します。

- リクエストとレスポンスのキューの詳細

- 再試行回数と遅延

次の表で定義されているレベルで、Webサービス永続性を構成できます。

表21-4 Webサービス永続性の構成

レベル

説明

WebLogic Server

サーバー・レベルで構成されたWebサービス永続性では、そのサーバーで実行しているすべてのWebサービスとクライアントのデフォルトの構成を定義します。WebLogic Serverに対してWebサービス永続性を構成するには、次のいずれかの方法を使用します。

- 構成ウィザードを使用してドメインを作成または拡張するときに、WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を適用して、Webサービス永続性をサポートするために必要なリソースを自動的に構成できます。
この拡張テンプレートの使用は必須ではありませんが、使用すると必要なリソースの構成が格段に容易になります。

- Webサービス永続性に必要なリソースを、Oracle WebLogic管理コンソールまたはWLSTを使用して構成します。詳細については、以下を参照してください。
- WebLogic Server管理コンソール: Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービス永続性の構成に関する項

- WLST: 『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項

詳細は、「高度なWebサービス機能のためのドメインの構成」を参照してください。

Webサービス・エンドポイント

Webサービス・エンドポイントによって使用されるデフォルトの論理ストアを構成します(「Webサービス・エンドポイントのWebサービス永続性の構成」を参照)。

Webサービス・クライアント

Webサービス・クライアントによって使用されるデフォルトの論理ストアを構成します(「Webサービス・クライアントのWebサービス永続性の構成」を参照)。

次の項では、Webサービス永続性の構成について詳細に説明します。

- 論理ストアの構成

- Webサービス・エンドポイントのWebサービス永続性の構成

- Webサービス・クライアントのWebサービス永続性の構成

論理ストアの構成

アプリケーション環境内で使用する1つ以上の論理ストアを構成し、デフォルトとして使用する論理ストアを指定できます。

デフォルトの論理ストアWseeStoreは、WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を使用してドメインを作成または拡張するときに、自動的に生成されます(「高度なWebサービス機能のためのドメインの構成」を参照)。

WebLogic Server管理コンソールを使用して論理ストアを構成できます。Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービス永続性の構成に関する項を参照してください。または、WLSTを使用してリソースを構成できます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

次の表では、論理ストアに対して定義できるプロパティを説明します。

表21-5 論理ストアの構成プロパティ

プロパティ

説明

デフォルト論理ストア名

論理ストアの名前。名前はアルファベット文字から始める必要があり、アルファベット文字、スペース、ダッシュ、アンダースコア、数字のみを使用できます。

このフィールドのデフォルトはLogicalStore_nです。このフィールドは必須です。

Webサービス拡張テンプレートを使用して単一のサーバー・ドメインを作成または拡張する場合は、WseeStoreという名前の論理ストアがデフォルトで作成されます。

デフォルト論理ストア

サーバー上のすべてのWebサービスの状態を永続化するためにデフォルトで使用する論理ストアかどうかを指定するフラグ。

デフォルトとして設定できる論理ストアは1つだけです。現在の論理ストアでこのフラグを有効にした場合、現在のデフォルト・ストアではフラグが無効になります。

永続性戦略

永続性戦略です。ドロップダウン・メニューから次のいずれかの値を選択します。

- ローカル・アクセスのみ: ローカル・サーバーだけがアクセスできます。

- メモリー内: ローカルVMのみがアクセスできます。この場合、バッファリング・キューと物理ストアの構成情報は無視されます。

リクエスト・バッファリング・キューのJNDI名

リクエスト・バッファリング・キューのJNDI名。リクエスト・バッファリング・キューは、関連付けによって物理ストアを類推するために使用されます。このプロパティを設定しない場合、サーバーに対して構成されているデフォルトの物理ストアが使用されます。

注意: 物理ストアとバッファリング・キューは、両方ではなく、どちらか一方のみを構成します。バッファリング・キューを構成すると、物理ストアの情報は類推されます。

より効率的な単一フェーズのXAトランザクションを可能にし、サービスの移行を容易にするため、永続状態とメッセージ・バッファリングの両方で同じ物理ストレージ・リソースを使用することをお薦めします。この値を設定することで、バッファリング・キューと物理ストアが同じ物理ストレージ・リソースを参照することが保証されます。

Webサービス拡張テンプレートを使用してドメインを作成または拡張する場合は、weblogic.wsee.BufferedRequestQueueという名前のバッファリング・キューがデフォルトで作成されます。

注意: 永続性戦略を「メモリー内」に設定すると、このプロパティは無視されます。

レスポンス・バッファリング・キューのJNDI名

レスポンス・バッファリング・キューのJNDI名。

このプロパティを設定しない場合は、「リクエスト・バッファリング・キューのJNDI名」プロパティで定義されているリクエスト・キューが使用されます。

Webサービス拡張テンプレートを使用してドメインを作成または拡張する場合は、weblogic.wsee.BufferedRequestErrorQueueという名前のバッファリング・キューがデフォルトで作成されます。

注意: 永続性戦略を「メモリー内」に設定すると、このプロパティは無視されます。

クリーナの間隔

論理ストアをクリーンアップする間隔。詳細は、「Webサービス永続性のクリーンアップ」を参照してください。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはPT10M (10分)です。

注意: このフィールドは、論理ストアを編集するときにのみ使用できます。論理ストアを作成するときは、このフィールドはデフォルトでPT10M (10分)に設定されます。

デフォルト最大オブジェクト存続期間

オブジェクトの最大存続期間として使用されるデフォルト値。この値は、論理ストアに保存される個別のオブジェクトでオーバーライドできます。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP1D (1日)です。

注意: このフィールドは、論理ストアを編集するときにのみ使用できます。論理ストアを作成するときは、このフィールドはデフォルトでP1D (1日)に設定されます。

Webサービス・エンドポイントのWebサービス永続性の構成

デフォルトでは、Webサービス・エンドポイントはサーバーに対して定義されているWebサービス永続ストアを使用します。Webサービス・エンドポイントによって使用される論理ストアは、WebLogic Server管理コンソールを使用してオーバーライドできます。詳細は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービス永続性の構成に関する項を参照してください。

Webサービス・クライアントのWebサービス永続性の構成

Webサービス・クライアント永続性の構成の詳細は、「Webサービス・クライアントの構成」を参照してください。

クラスタでのWebサービス永続性の使用

クラスタでWebサービス永続性を使用するための考慮事項を次に示します。

- WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を使用してクラスタ・ドメインを作成または拡張する場合、クラスタでWebサービス永続性をサポートするために必要なリソースが自動的に作成されます。詳細は、「高度なWebサービス機能のためのドメインの構成」を参照してください。

- サービスの移行を容易にするため、永続状態とメッセージ・バッファリングの両方に同じ物理ストレージ・リソースを使用することをお薦めします。バッファリング・キューと物理ストアが同じ物理ストレージ・リソースを参照するようにするには、「論理ストアの構成」で説明されているように、論理ストアの「リクエスト・バッファリング・キューのJNDI名」プロパティを構成します。

- バッファリング・キューはJMS Uniform Distributed Destination (UDD)として定義することをお薦めします。JMSでは、指定する各JMSサーバーのUDDにメンバー・キューが定義されます。論理ストアは定義されているバッファリング・キューによって物理ストアと関連付けられるので、これにより、サービスの移行の間に、論理ストアは、新しいサーバーに移行されるメンバー・キューの新しい物理ストアをシームレスに使用できます。

- JMSサーバー、Store-And-Forward (SAF)サービス・エージェント、物理ストア(ファイル・ストア)リソースを移行可能なターゲットにすることをお薦めします。詳細は、「高度なWebサービス機能に必要なリソース」を参照してください。

たとえば、図21-2で示されている2ノードのクラスタ構成を考えます。ドメイン・リソースは、前記のガイドラインを使用して構成およびターゲット指定されます。

図21-2 2ノード・クラスタ構成の例(移行前)

次の図では、Server1で障害が発生した場合にServer1上のリソースをServer2に簡単に移行する方法を示します。

図21-3 2ノード・クラスタ構成の例(移行後)

Webサービス永続性のクリーンアップ

永続化された情報は、期限切れまたは失効したオブジェクトを削除するために、定期的にクリーンアップされます。通常、オブジェクトは特定の有効期限または最大存続期間と関連付けられています。さらに、失効したオブジェクトは、レスポンスを受信しなかったリクエスト、または明示的に終了されなかった信頼性のあるメッセージング・シーケンスを表す場合があります。

Webサービス永続性がクリーンアップされる間隔は、論理ストアの「クリーナの間隔」構成プロパティで構成します。このプロパティの設定の詳細は、「論理ストアの構成」を参照してください。

22 Webサービスのメッセージ・バッファリングの構成

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスのメッセージ・バッファリングを構成する方法について説明します。

この章の内容は次のとおりです:

- メッセージ・バッファリングの概要

- メッセージ・バッファリングの構成

メッセージ・バッファリングの概要

バッファリングされたWebサービス上の操作が呼び出されると、その呼出しを表すメッセージがJMSキューに格納されます。WebLogic Serverは、このバッファリングされたメッセージを非同期に処理します。メッセージがまだキュー内にある間にWebLogic Serverがダウンした場合、WebLogic Serverが再起動するとすぐに処理されます。

WebLogic Serverは、あらかじめ構成されて管理されたスレッドのプールから取得した別のスレッドで、リクエスト・メッセージを処理します。これにより、WebLogic Serverはクライアントの負荷のスパイクを緩和し、リクエストの時間順の処理を続けることができます。メッセージ・バッファリングは、サービス拒否攻撃とサーバーでの一般的な過負荷状態を防ぐための強力なツールです。

Webサービスにメッセージ・バッファリングを構成するかどうかを判断するための参考に、「バッファなしの信頼性のあるWebサービスでの障害シナリオ」を確認することをお薦めします。

メッセージ・バッファリングの構成

WebLogic ServerまたはWebサービス・エンドポイントのレベルで、Webサービスにメッセージ・バッファリングを構成できます。サーバー・レベルで構成されたメッセージ・バッファリングでは、Webサービス・エンドポイント・レベルで明示的にオーバーライドされないかぎり、そのサーバー上で実行するすべてのWebサービスとクライアントに対するデフォルトのメッセージ・バッファリングが定義されます。

WebLogic Server管理コンソールを使用してWebLogic ServerまたはWebサービス・エンドポイントのレベルでWebサービスに対するメッセージ・バッファリングを構成する詳細な手順は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのWebサービスに対するメッセージ・バッファリングの構成に関する項を参照してください。

Webサービス・エンドポイント・レベルでメッセージ・バッファリングを構成するときは、「バッファリング構成のカスタマイズ」を選択し、Webサービス記述子またはデプロイメント・プランで定義されているバッファリング構成をWebサービス・エンドポイント・レベルでカスタマイズすることを指定します。これを選択しないと、WebLogic Serverレベルで指定されているバッファリング構成が使用されます。

または、WLSTを使用して、メッセージ・バッファリングを構成することもできます。WLSTを使用したドメインの拡張の詳細は、『WebLogic Scripting Toolの理解』の既存ドメインの構成に関する項を参照してください。

次の項では、メッセージ・バッファリングの構成プロパティについて説明します。

- リクエスト・キューの構成

- レスポンス・キューの構成

- メッセージの再試行回数と遅延の構成

リクエスト・キューの構成

次の表では、リクエスト・キューの構成に使用するプロパティを説明します。

表22-1 リクエスト・キューの構成

プロパティ

説明

リクエスト・キューの有効化

リクエスト・キューが有効かどうかを指定するフラグ。デフォルトでは、リクエスト・キューは無効です。リクエスト・キューの名前は、そのレベルで有効な論理ストアによって定義されます。

WebLogic Server永続ストアを論理ストアの物理ストアとして使用すると、リクエスト・バッファリング・キューとレスポンス・バッファリング・キューの名前はバッファリングの構成ではなく論理ストアの構成から取得されます。

リクエスト・キューの接続ファクトリのJNDI名

リクエスト・メッセージ・バッファリングに使用する接続ファクトリのJNDI名。この値のデフォルトは、サーバーで定義されているデフォルトのJMS接続ファクトリです。

リクエスト・キュー・トランザクションの有効化

リクエスト・バッファリング・キューのメッセージを格納および取得するときにトランザクションを使用するかどうかを指定するフラグ。デフォルトはfalseです。

レスポンス・キューの構成

次の表では、レスポンス・キューの構成に使用するプロパティを説明します。

表22-2 レスポンス・キューの構成

プロパティ

説明

レスポンス・キューの有効化

レスポンス・キューが有効かどうかを指定するフラグ。デフォルトでは、レスポンス・キューは無効です。レスポンス・キューの名前は、そのレベルで有効な論理ストアによって定義されます。

WebLogic Server永続ストアを論理ストアの物理ストアとして使用すると、リクエスト・バッファリング・キューとレスポンス・バッファリング・キューの名前はバッファリングの構成ではなく論理ストアの構成から取得されます。

レスポンス・キューの接続ファクトリのJNDI名

レスポンス・メッセージ・バッファリングに使用する接続ファクトリのJNDI名。この値のデフォルトは、サーバーで定義されているデフォルトのJMS接続ファクトリです。

レスポンス・キュー・トランザクションの有効化

レスポンス・バッファリング・キューのメッセージを格納および取得するときにトランザクションを使用するかどうかを指定するフラグ。デフォルトはfalseです。

メッセージの再試行回数と遅延の構成

次の表では、メッセージの再試行回数と遅延の構成に使用するプロパティを説明します。

表22-3 メッセージの再試行回数と遅延の構成

プロパティ

説明

再試行回数

呼び出されたWebLogic ServerインスタンスのJMSキューが、操作が正常に呼び出されるまでWebサービスの実装にメッセージの配信を試みる回数。この値のデフォルトは3。

再試行の遅延

バッファリングされたリクエストとレスポンスの再試行の間隔。この値は、「再試行回数」が0より大きいときにのみ適用されます。

指定する値はXMLスキーマの期間を表す字句形式(PnYnMnDTnHnMnS)に従った正の値でなければなりません。ここで、nYは年数、nMは月数、nDは日数を表し、Tは日付/時刻のセパレータ、nHは時間数、nMは分数、nSは秒数を表します。この値のデフォルトはP0DT30S (30秒)です。

23 クラスタ内のWebサービスの管理

この章では、クラスタ内のWebLogic Server 12.1.3用のWebLogic Webサービスの管理方法について説明します。

この章の内容は次のとおりです:

- Webサービス・クラスタでのルーティングの概要

- クラスタでのルーティングのシナリオ

- Webサービス・クラスタでのルーティングの仕組み

- クラスタ内のWebサービスの構成

- クラスタのルーティング・パフォーマンスのモニター

注意:
クラスタでのWebサービス永続性の使用に関する考慮事項は、「クラスタでのWebサービス永続性の使用」を参照してください。

Webサービス・クラスタでのルーティングの概要

ステートレスWebサービス(それまでの起動における状態情報を認識している必要のないサービス)のクラスタリングは単純であり、サード・パーティのHTTPロード・バランサに対して既存のWebLogic HTTPルーティング機能と連携して動作します。

状態情報のメンテナンスが必要なWebサービスのクラスタリングには課題がいくつかあります。そのようなWebサービスの各インスタンスは状態情報に関連付けられており、この状態情報を管理し、保持する必要があります。クラスタでのルーティングの決定は、メッセージがクラスタ内の特定のサーバーにバインドされているかどうかに基づいて行われます。たとえば、メッセージの処理に必要な状態情報が特定のサーバーに格納されいる場合、その状態情報はそのサーバーでローカルに使用することしかできません。

注意:
セッション状態レプリケーションを使用して状態を管理するサービスは、Reliable Secure ProfileのようなWebサービスの高度な機能を利用するサービスとは問題の種類が異なります。後者では、ローカル・サーバーのみで利用できる状態の格納を備えるなど、永続性に関してより堅牢なアプローチが必要です。詳細は、「永続性に関する注意」を参照してください。

Webサービス・リクエストが適切なサーバーにルーティングされるようにするだけでなく、クラスタリングに関する次の一般的な要件を満たす必要があります。

- クラスタの内部トポロジは、クライアントに対して透過的にする必要があります。クライアントは、フロントエンド・ホストのみを介してクラスタと相互通信するため、クラスタ内の特定のサーバーを認識する必要はありません。これによって、クラスタは時間をかけて拡張し、需要を満たすことができます。

- クラスタの移行がクライアントに対して透過的に行われることが必要です。クラスタ内のリソース(永続ストアなど、WebサービスまたはWebサービス・クライアントに必要なリソース)は、クラスタの拡大や障害対応などの理由で、あるサーバーから別のサーバーへ移行できます。

クラスタ内のWebサービスのルーティングについては、前述の要件に合せて、次の方式が用意されています。

- インプレースSOAPルーター: リクエスト・メッセージが正しいサーバーに届き、そうでない場合は正しいサーバーに転送されることを前提としています(追加ホップは最大1回)。ルーティングの決定は、メッセージを受信するWebサービスが行います。このルーティング戦略は実装が最も簡単であり、構成も必要ありません。ただし、次の方式に比べると堅牢性に劣ります。

- フロントエンドSOAPルーター (HTTPクラスタ・サーブレットのみ): メッセージ・ルーティングは、クラスタのかわりにメッセージを受け入れるフロントエンド・ホストによって管理され、クラスタの選択メンバー・サーバーに転送します。Webサービスの場合、フロントエンドSOAPルーターは、SOAPメッセージ内の情報を検査し、メッセージをルーティングする先の正しいサーバーを決定します。
このルーティング戦略は構成が複雑ですが、メッセージが適切なサーバーに直接ルーティングされるため効率的です(追加ホップは発生しません)。

注意:
「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」の説明に従って接続作成を使用するとき、所定の接続作成匿名URIに関連するすべてのメッセージの適切なルーティングを保証できるのはフロントエンドSOAPルーティングのみです。

この章では、クラスタ内のWebサービスのルーティングが最適化されるように環境を構成する方法について説明します。フロントエンドSOAPルーターとしてのHTTPクラスタ・サーブレットの使用についても説明します。また、インプレースSOAPルーターを有効化し、HTTPクラスタ・サーブレットが使用できない場合や初期化されていない場合に使用します。

永続性に関する注意

「HTTPセッションを使用したステートフルJAX-WS Webサービスのプログラミング」で説明されているように、一部のケースではHttpSessionを使用してWebサービスの状態を維持できますが、この単純な永続性には十分な堅牢性がありません。Webサービスの高度な機能(信頼性のあるメッセージング、接続作成、Secure Conversationなど)では堅牢な永続性が要件となっており、HttpSessionのみを使用して満たすことはできません。Webサービスの高度な機能は、論理ストアという概念に基づいた専用の永続性実装を使用します。詳細は、「Webサービス永続性の管理」を参照してください。

現時点では、Webサービス状態の永続性に関するこの2つのアプローチには互換性がありません。HttpSession永続性を使用するクラスタ化ステートフルWebサービスの作成を選択してから、(クライアントまたはサービスとして)そのサービスでWebサービスの高度な機能を使用すると、クラスタにおけるサービスの正常な動作が保証されません。これは、HttpSessionレプリケーションが、Webサービスの高度な機能の永続性をホストするのではなく、様々なサーバー・セットでHttpSessionを使用可能にできるためです。

クラスタでのルーティングのシナリオ

次の項では、クラスタ環境内でWebサービスのリクエスト・メッセージとレスポンス・メッセージをルーティングする際のシナリオについて、図を使用して説明します。

- シナリオ1: 単一サーバーへのWebサービス・レスポンスのルーティング

- シナリオ2: ルーティング情報を使用した単一サーバーへのWebサービス・レスポンスのルーティング

- シナリオ3: IDを使用した単一サーバーへのWebサービス・レスポンスのルーティング

シナリオ1: 単一サーバーへのWebサービス・レスポンスのルーティング

このシナリオでは、受信したリクエストがサーバーに対してロード・バランシングされます。そのリクエストへのレスポンスをすべて、その同じサーバーにルーティングすることによって、元のリクエストにかわって状態情報を保持する必要があります。

図23-1 単一サーバーへのWebサービス・レスポンスのルーティング

前の図に示すように、次のような処理が行われます。

1. フロントエンドSOAPルーターが、受信したHTTPリクエストをルーティングし、標準的なロード・バランシング手法でServer2に送信します。

2. Server2が、Webサービスのエンドポイント・アドレスにあるMyserviceを呼び出します。SOAPメッセージのReplyToヘッダーには、フロントエンドSOAPルーターへのポインタが含まれています。

3. MyServiceがフロントエンドSOAPルーターにレスポンスを戻します。

4. フロントエンドSOAPルーターは、レスポンスのルーティング先を決定する必要があります。Server2がレスポンスに関連する状態情報を保持しているため、フロントエンドSOAPルーターはレスポンスをServer2にルーティングします。

シナリオ2: ルーティング情報を使用した単一サーバーへのWebサービス・レスポンスのルーティング

このシナリオでは、受信したリクエストがサーバーに対してロード・バランシングされます。レスポンスには、後続のリクエストに関する元のサーバーを宛先とするルーティング情報が含まれています。

図23-2 単一サーバーへのWebサービス・リクエストのルーティング

前の図に示すように、次のような処理が行われます。

1. フロントエンドSOAPルーターが、受信したHTTPリクエスト(Request1)をルーティングし、標準的なロード・バランシング手法でServer2に送信します。リクエストにはルーティング情報は含まれていません。

2. Server2が、Webサービスのエンドポイント・アドレスにあるMyserviceを呼び出します。SOAPメッセージのReplyToヘッダーには、フロントエンドSOAPルーターへのポインタが含まれています。

3. MyServiceが呼出し元にレスポンスを戻します。レスポンスには、Server2を後続のすべてのリクエストのターゲットに指定するルーティング情報が含まれています。呼出し元は、レスポンスに含まれているルーティング情報を、後続のすべてのリクエスト(Request2など)に入れて渡します。

4. フロントエンドSOAPルーターが、Request2とともに渡されたルーティング情報を使用して、Request2をServer2にルーティングします。

シナリオ3: IDを使用した単一サーバーへのWebサービス・レスポンスのルーティング

このシナリオでは、受信したSOAPリクエストにIDが含まれていますが、ルーティング情報は含まれていません。同じIDを持つ後続のリクエストはすべて、同じサーバーに送られる必要があります。

図23-3 IDを使用した単一サーバーへのWebサービス・レスポンスのルーティング

前の図に示すように、次のような処理が行われます。

1. リクエストは、ID (接続作成匿名URI)を含むWebサービス・クライアントに由来し、このIDはRequest1に関連する将来のリクエストによって共有されます。このIDのフォームはプロトコル固有のものです。

2. フロントエンドSOAPルーターがRequest1のIDを検出し、アフィニティ・ストアをチェックして、そのIDがクラスタ内の特定のサーバーに関連付けられていないかを調べます。この場合、関連付けは定義されていません。

3. フロントエンドSOAPルーターがリクエストのロード・バランシングを行い、処理のためにリクエストをServer2に送信します。

4. Server2のMyService Webサービス・インスタンスがリクエストを処理します(必要に応じてレスポンスを生成します)。この場合、シナリオ2: ルーティング情報を使用した単一サーバーへのWebサービス・レスポンスのルーティングとは異なり、ルーティング情報は伝播できません。

5. Request1で使用したのと同じIDを使用して、Request2がフロントエンドSOAPルーターに到着します。

6. フロントエンドSOAPルーターがIDを検出し、アフィニティ・ストアをチェックして、そのIDが特定のサーバーに関連付けられていないかを調べます。この場合、IDがServer2にマップされていることが判明します。

7. アフィニティ情報に基づいて、フロントエンドSOAPルーターがRequest2をServer2にルーティングします。

Webサービス・クラスタでのルーティングの仕組み

次の項では、Webサービス・クラスタでのルーティングの仕組みについて説明します。

- 送信するリクエストへのルーティング情報の追加

- 受信したリクエストのルーティング情報の検出

- クラスタ内でのリクエストのルーティング

- フロントエンドSOAPルーターでのルーティング・マップの保持

送信するリクエストへのルーティング情報の追加

Webサービス・ランタイムは、次のような場合でもメッセージのルーティングが適切に行われるよう、送信するすべてのメッセージのSOAPヘッダーにルーティング情報を追加します。

- リクエストの送信元のWebサービス・クライアントが、クラスタに属するすべてのサーバーからはアクセスできないストアを使用している場合。

- リクエストが、レスポンスの処理に使用されるメモリー内の状態情報を必要とする場合。

送信するメッセージを処理する際、Webサービス・ランタイムは次のことを実行します。

- 送信するリクエストにメッセージIDが割り当てられていない場合はメッセージIDを作成し、RelatesTo/MessageID SOAPヘッダーに次の形式で格納します。
uuid:WLSformat_version:store_name:uniqueID

説明:

- format_versionには、WebLogic Server形式のバージョン(WLS1など)を指定します。

- store_nameには、永続ストア(メッセージを送信する現在のWebサービスまたはWebサービス・クライアントによって使用されるストア)の名前を指定します。たとえば、Server1Storeです。この値は、システムで生成される名前(デフォルトの永続ストアを使用する場合)または空の文字列(永続ストアが構成されていない場合)です。

- unique_IDには、一意のメッセージIDを指定します。例:68d6fc6f85a3c1cb:-2d3b89ab8:12068ad2e60:-7febです。

- 他のWebサービス・コンポーネントが、メッセージにルーティング情報を組み込んでからメッセージを送信できるようにします。

受信したリクエストのルーティング情報の検出

SOAPルーター(インプレースまたはフロントエンド)は、受信したリクエストにルーティング情報がないかチェックします。特に、SOAPルーターはRelatesTo/MessageID SOAPヘッダーを探して永続ストアの名前を特定し、その永続ストアをホストするサーバーにメッセージを戻します。

フロントエンドSOAPルーティングを使用して正しいサーバーを判別する際にエラーが発生した場合、メッセージはクラスタ内のいずれかのサーバーに送信され、インプレースSOAPルーターが使用されます。インプレースSOAPルーターでフォルトが発生した場合、メッセージの送信元はプロトコル固有のバック・チャネルでフォルトを受信します。

注意:
ルーティング情報を含むSOAPメッセージ・ヘッダーは、平文で表す必要があります。暗号化することはできません。

クラスタ内でのリクエストのルーティング

ルーティングの決定を助けるため、SOAPルーター(インプレースまたはフロントエンド)はストアとサーバーの名前の関連付けを表す動的マッピングを使用します。この動的マップはクラスタ内の管理対象サーバーで作成されたもので、インプレースSOAPルーターはメモリー内でアクセスし、フロントエンドSOAPルーターはHTTPレスポンス・ヘッダーを介してアクセスします。HTTPレスポンス・ヘッダーは、クラスタ内のWebサービスから送信されたすべてのHTTPレスポンスに自動的に組み込まれます。

注意:
HTTPレスポンス・ヘッダーの詳細は、「フロントエンドSOAPルーターでのルーティング・マップの保持」を参照してください。

当初、動的マップは空です。初期化されるのは、クラスタ内の管理対象サーバーから最初のレスポンスを受信した後です。HTTPレスポンス・ヘッダーを含む最初のレスポンスを受信するまで、フロントエンドSOAPルーターは単にリクエストのロード・バランシングを行い、インプレースSOAPルーターはリクエストを適切なサーバーにルーティングします。

SOAPベースのルーティング情報がない場合、単純なロード・バランシング(ラウンドロビンなど)が行われている、HTTPセッション・ベースのルーティングを含むベース・ルーティングに従います。

フロントエンドSOAPルーターでのルーティング・マップの保持

「クラスタ内でのリクエストのルーティング」で述べたように、ルーティングの決定を助けるため、SOAPルーター(インプレースまたはフロントエンド)はストアとサーバーの名前の関連付けを表す動的マッピングを使用します。

この動的マップを生成するために、2つの新しいHTTPレスポンス・ヘッダーが用意されています(この後の項を参照)。これらのヘッダーは、クラスタ内のWebサービスから送信されたすべてのHTTPレスポンスに自動的に組み込まれます。

注意:
サード・パーティのフロントエンドを実装する際は、この後説明するHTTPレスポンス・ヘッダーを組み込むために、変数X-weblogic-wsee-request-storetoserver-listを任意の値に設定したHTTPリクエスト・ヘッダーを、クライアントから送信する必要があります。

X-weblogic-wsee-storetoserver-list HTTPレスポンス・ヘッダー

ストアとサーバーのマッピングの一覧は、X-weblogic-wsee-storetoserver-list HTTPレスポンス・ヘッダーに保持されます。フロントエンドSOAPルーターは、このヘッダーを使用して、実行時に参照可能なマッピングにデータを移入し、メッセージのルーティングを行います。

X-weblogic-wsee-storetoserver-list HTTPレスポンス・ヘッダーは次の形式を取ります。

storename1:host_server_spec | storename2:host_server_spec | storename3:host_server_spec

各値の説明は次のとおりです。

- storenameには、永続ストアの名前を指定します。

- host_server_specには、servername:host:port:sslportという形式で指定します。不明な場合、sslportは-1に設定されます。

X-weblogic-wsee-storetoserver-hash HTTPレスポンス・ヘッダー

ストアとサーバーのリストのハッシュ・マッピングは、X-weblogic-wsee-storetoserver-hash HTTPレスポンス・ヘッダーに指定されます。このヘッダーを使用すると、新しいマッピング・リストをリフレッシュする必要があるかどうかを判断できます。

X-weblogic-wsee-storetoserver-hash HTTPレスポンス・ヘッダーには、X-weblogic-wsee-storetoserver-list HTTPレスポンス・ヘッダーに含まれるリストのハッシュ値を表す文字列値が組み込まれます。リストの最後のエントリを追跡することで、リストのリフレッシュが必要かどうかを判断できます。

クラスタ内のWebサービスの構成

次の表に、クラスタ内のWebサービスを構成する手順をまとめます。

表23-1 クラスタ内のWebサービスを管理する手順

#

手順

説明

1

WebLogicクラスタを設定します。

「WebLogicクラスタの設定」を参照してください。

2

Webサービスの高度な機能に必要なクラスタ・ドメイン・リソースを構成します。

クラスタ拡張テンプレート・スクリプトを使用すると、必要なクラスタ・ドメイン・リソースを自動的に構成できます。もう1つの方法として、Oracle WebLogic Server管理コンソールまたはWLSTを使用し、リソースを構成することも可能です。「クラスタ環境におけるWebサービスの高度な機能に必要なドメイン・リソースの構成」を参照してください。

3

フロントエンドSOAPルーターを拡張してWebサービスをサポートします。

注意: この手順は、フロントエンドSOAPルーターを使用する場合のみ必要です。

Webサービス・ルーティング・サーブレットは、WebLogic HTTPクラスタ・サーブレットの機能を拡張して、クラスタ内のWebサービスのルーティングをサポートします。「フロントエンドSOAPルーターの拡張によるWebサービスのサポート」を参照してください。

4

Webサービス原子性トランザクション・メッセージのルーティングを有効にします。

「Webサービス原子性トランザクション・メッセージのルーティングの有効化」を参照してください。

5

Webサービスの接続作成メッセージのルーティングを有効にします。

「Webサービスの接続作成メッセージのルーティングの有効化」を参照してください。

6

フロントエンドSOAPルーターのIDを構成します。

クラスタ内の各WebLogic ServerインスタンスをフロントエンドSOAPルーターのアドレスおよびポートで構成する必要があります。「フロントエンドSOAPルーターのIDの構成」を参照してください。

WebLogicクラスタの設定

『Oracle WebLogic Serverクラスタの管理』のWebLogicクラスタの設定に関する項の説明に従って、WebLogicクラスタを設定します。次の点に注意してください。

- クラスタ・ドメインを構成するには、「クラスタ環境におけるWebサービスの高度な機能に必要なドメイン・リソースの構成」を参照してください。

- SOAPベースのフロントエンドSOAPルーティングを有効にするには、『Oracle WebLogic Serverクラスタの管理』のHttpClusterServletの設定に関する項の説明に従って、HTTPクラスタ・サーブレットを構成します。

クラスタ環境におけるWebサービスの高度な機能に必要なドメイン・リソースの構成

構成ウィザードを使用してドメインの作成または拡張を行う際には、WebLogic Advanced Web Services for JAX-WS拡張テンプレート(wls_webservice_jaxws.jar)を適用すると、クラスタ環境でWebサービスの高度な機能をサポートするのに必要なリソースを自動的に構成できます。この拡張テンプレートの使用は必須ではありませんが、使用すると必要なリソースの構成が格段に容易になります。あるいは、Oracle WebLogic Server管理コンソールまたはWLSTを使用して、これらの高度な機能に必要なリソースを構成できます。

また、テンプレートによって、ドメインの変化(サーバーの追加や削除など)に合せて、高度なWebサービスで必要なリソースを管理するために使用できるスクリプトがドメイン・ディレクトリにインストールされます。

ドメインを構成して、リソースを管理するスクリプトを実行する方法の詳細は、「高度なWebサービス機能のためのドメインの構成」を参照してください。

フロントエンドSOAPルーターの拡張によるWebサービスのサポート

注意:
フロントエンドSOAPルーターを使用しない場合、この手順は不要です。

フロントエンドSOAPルーターを拡張してWebサービスをサポートするには、次の例(太字の部分)に示すRoutingHandlerClassNameパラメータを、WebLogic HTTPクラスタ・サーブレット定義の一部として指定します。

<!DOCTYPE web-app PUBLIC
"-//Sun Microsystems, Inc.//DTD Web Application 2.3//EN"
"http://java.sun.com/dtd/web-app_2_3.dtd">
<web-app>
<servlet>
<servlet-name>HttpClusterServlet</servlet-name>
<servlet-class>weblogic.servlet.proxy.HttpClusterServlet</servlet-class>
<init-param>
<param-name>WebLogicCluster</param-name>
<param-value>Server1:7001|Server2:7001</param-value>
</init-param>
<init-param>
<param-name>RoutingHandlerClassName</param-name>
<param-value>
weblogic.wsee.jaxws.cluster.proxy.SOAPRoutingHandler
</param-value>
</init-param>
</servlet>
<servlet-mapping>
<servlet-name>HttpClusterServlet</servlet-name>
<url-pattern>/</url-pattern>
</servlet-mapping>
. . .
</web-app>

Webサービス原子性トランザクション・メッセージのルーティングの有効化

Webサービス原子性トランザクション・メッセージの高可用性およびルーティングは、Webサービスのクラスタ環境では自動的に有効になります。ただし、WebLogic HTTPクラスタ・サーブレットがフロントエンド・サーバーとして使用されている場合は、WebLogic HTTPクラスタ・サーブレットをホストするサーバーで、次のシステム・プロパティをfalseに設定する必要があります。

weblogic.wsee.wstx.wsat.deployed=false

また、WebLogic Serverプラグインを使用するときは、WLIOTimeoutSecsパラメータ値を適切に構成する必要があります。このパラメータは、WebLogic Serverからのリクエストに対するレスポンスをプラグインが待機する時間を定義します。サーブレットの処理時間より短くした場合は、予期しない結果が発生する場合があります。WLIOTimeoutSecsパラメータの詳細は、Oracle WebLogic Serverプロキシ・プラグイン12.1.3の使用のWebサーバー・プラグインの一般的なパラメータに関する項を参照してください。

Webサービスの接続作成メッセージのルーティングの有効化

Webサービスの接続作成をサポートするには、「ファイアウォールの内側からの非同期Webサービス・クライアントの使用(接続作成)」に記載されているように、WebLogic HTTPクラスタ・サーブレットをホストしているWebLogic Server上にデフォルトの論理ストアを構成する必要があります。デフォルトの論理ストアの構成の詳細は、「論理ストアの構成」を参照してください。

フロントエンドSOAPルーターのIDの構成

クラスタ内の各WebLogic ServerインスタンスをフロントエンドSOAPルーターのアドレスおよびポートで構成する必要があります。

次の方法(優先度の高い順にリストされています)のいずれかを使用して、フロントエンドSOAPルーターのIDを構成できます。

- 「ネットワーク・チャネルを使用したフロントエンドSOAPルーターのIDの構成」の説明に従って、ネットワーク・チャネルを作成します。これがお薦めする方法です。

- Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタ用のHTTP設定の構成に関する項の説明に従って、クラスタのフロントエンド・ホストとポートを構成します。

- Oracle WebLogic Server管理コンソール・オンライン・ヘルプのHTTPプロトコルの構成に関する項の説明に従って、ローカル・サーバーのフロントエンド・ホストとポートを構成します。

- Oracle WebLogic Server管理コンソール・オンライン・ヘルプのクラスタの構成に関する項の説明に従って、クラスタのCluster Addressを定義します。Cluster Addressは、他の値が設定されていない場合に必要となります。

ネットワーク・チャネルを使用したフロントエンドSOAPルーターのIDの構成

ネットワーク・チャネルを使用すると、クラスタのフロントエンド・アドレスにアクセスするための一貫した方法を提供できます。ネットワーク・チャネルの詳細は、『Oracle WebLogic Serverサーバー環境の管理』のネットワーク・チャネルの理解に関する項を参照してください。

ネットワーク・チャネルを使用して、フロントエンドSOAPルーターのIDを構成するには、サーバー・インスタンスごとに次の手順を実行します。

1. Webサービスの呼出しに使用するプロトコル用のネットワーク・チャネルを作成します。ネットワーク・チャネルの名前は、weblogic-wsee-proxy-channel-XXXとする必要があります(XXXはプロトコルを表します)。たとえば、HTTPS用のネットワーク・チャネルを作成する場合、weblogic-wsee-proxy-channel-httpsという名前にします。
ネットワーク・チャネルの作成に関する一般情報は、Oracle WebLogic Server管理コンソール・オンライン・ヘルプのカスタム・ネットワーク・チャネルの構成に関する項を参照してください。

2. 「外部リスニング・アドレス」および「外部リスニング・ポート」フィールドを、それぞれプロキシ・サーバーのアドレスおよびポートで更新して、ネットワーク・チャネルを構成します。

クラスタのルーティング・パフォーマンスのモニター

次のクラスタ・ルーティング統計をモニターすると、アプリケーションのパフォーマンスを評価できます。

- リクエストおよびレスポンスの総数。

- サーバーにルーティングされたリクエストおよびレスポンスの総数。

- ルーティングの失敗に関する情報(総数と最後の失敗を含む)。

WebLogic Server管理コンソールまたはWLSTを使用して、クラスタのルーティング・パフォーマンスをモニターできます。WebLogic Server管理コンソールを使用してクラスタのルーティング・パフォーマンスをモニターする方法については、『Oracle WebLogic Server Administration Consoleオンライン・ヘルプ』のSOAP Webサービスのモニターに関する項およびSOAP Webサービス・クライアントのモニターに関する項を参照してください。

24 プロバイダベース・エンドポイントおよびディスパッチ・クライアントを使用したSOAPメッセージの操作

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスに対し、XMLメッセージ・レベルでSOAPメッセージの処理を行うWebサービス・プロバイダベース・エンドポイントおよびディスパッチ・クライアントを開発する方法を説明します。

この章の内容は次のとおりです:

- Webサービス・プロバイダベース・エンドポイントおよびディスパッチ・クライアントの概要

- XMLレベルでの処理のための使用モードとメッセージ・フォーマット

- Webサービス・プロバイダベース・エンドポイントの開発(Javaから始める場合)

- Webサービス・プロバイダベース・エンドポイントの開発(WSDLから始める場合)

- プロバイダベース・エンドポイントでのSOAPハンドラの使用

- Webサービス・ディスパッチ・クライアントの開発

Webサービス・プロバイダベース・エンドポイントおよびディスパッチ・クライアントの概要

JAXB生成のクラスを使用する方が単純で処理速度が速く、エラーになる可能性も低いですが、場合によってはXMLメッセージ・コンテンツを直接処理するために独自のビジネス・ロジックを生成する必要があります。メッセージレベルのアクセスは、サーバー側ではWebサービス・プロバイダベース・エンドポイントを使用して、クライアント側ではディスパッチ・クライアントを使用して実行できます。

Webサービス・プロバイダベース・エンドポイントは、Javaサービス・エンドポイント・インタフェース(SEI)ベースのエンドポイントにかわる動的なエンドポイントを提供します。JavaオブジェクトとそのXML表現の変換の詳細を概念化するSEIベースのエンドポイントとは異なり、プロバイダ・インタフェースでは、JAXBバインディングなしでXMLメッセージ・レベルのコンテンツに直接アクセスできます。Webサービス・プロバイダベース・エンドポイントは、javax.xml.ws.Provider<T>またはcom.sun.xml.ws.api.server.AsyncProvider<T>インタフェースのそれぞれを使用して、同期的または非同期的に実装できます。Webサービス・プロバイダベース・エンドポイントの開発に関する詳細は、「Webサービス・プロバイダベース・エンドポイントの開発(Javaから始める場合)」を参照してください。

javax.xml.ws.Dispatch<T>インタフェースを使用して実装されるWebサービスのディスパッチ・クライアントは、クライアントがXMLレベルでメッセージを処理できるようにします。Webサービスのディスパッチ・クライアントを開発する手順は、「Webサービス・ディスパッチ・クライアントの開発」で説明します。

プロバイダ・エンドポイントとディスパッチ・クライアントは、WSDLが使用できるかぎり、次のような他のWebLogic Webサービス機能と連動して使用できます。

- WS-Security

- WS-ReliableMessaging

- WS-MakeConnection

- WS-AtomicTransaction

また、ディスパッチ・クライアントは、非同期クライアント・トランスポート機能および非同期クライアント・ハンドラ機能と組み合せて使用できます。これらの機能の詳細は、第12章「非同期クライアントの開発」および「ディスパッチ・インスタンスの作成」に示されているコード例を参照してください。

XMLレベルでの処理のための使用モードとメッセージ・フォーマット

プロバイダベース・エンドポイントまたはディスパッチ・クライアントを使用してXMLレベルでメッセージを処理するとき、次の表に定義する使用モードの1つを使用します。使用モードは、「使用モードの指定(@ServiceModeアノテーション)」の説明に従ってjavax.xml.ws.ServiceModeアノテーションを使用して定義します。

表24-1 XMLメッセージ・レベルでの処理のための使用モード

使用モード

説明

メッセージ

メッセージ全体を直接処理します。たとえば、SOAPバインディングが使用される場合、SOAPエンベロープ全体にアクセスします。

ペイロード

メッセージのペイロードのみを処理します。たとえば、SOAPバインディングが使用される場合、SOAP本体にアクセスします。

プロバイダベース・エンドポイントとディスパッチ・クライアントは、表24-2に定義されているメッセージ・フォーマットの1つを使用してメッセージを送受信できます。この表では、構成されているバインディング・タイプ(SOAP over HTTPまたはXML over HTTP)に対応する有効なメッセージ・フォーマットと使用モードの組合せも定義されます。

表24-2 XMLメッセージ・レベルでの処理でサポートされるメッセージ・フォーマット

メッセージ・フォーマット

SOAP/HTTPバインディングでサポートされる使用モード

XML/HTTPバインディングでサポートされる使用モード

javax.xml.transform.Source

メッセージ・モード: SOAPエンベロープ

ペイロード・モード: SOAP本体

メッセージ・モード: SourceとしてのXMLコンテンツ

ペイロード・モード: SourceとしてのXMLコンテンツ

javax.activation.DataSource

SOAP/HTTPバインディングの添付ファイルはSOAPMessageフォーマットを使用して送信されるため、どちらのモードでも有効ではありません。

メッセージ・モード: DataSourceオブジェクト

添付ファイルの送信にDataSourceが使用されるため、ペイロード・モードでは有効ではありません。

javax.xml.soap.SOAPMessage

メッセージ・モード: SOAPMessageオブジェクト

ペイロードのみではなくSOAPメッセージ全体が受信されるため、ペイロード・モードでは有効ではありません。

クライアントがSOAP以外のメッセージをXML/HTTPバインディングで送信できるため、どちらのモードでも有効ではありません。

Webサービス・プロバイダベース・エンドポイントの開発(Javaから始める場合)

次の項で説明されているように、同期および非同期のWebサービス・プロバイダベース・エンドポイントのどちらも開発できます。

- 同期プロバイダベース・エンドポイントの開発

- 非同期プロバイダベース・エンドポイントの開発

注意:
WSDLから始めて、ポートをWebサービス・プロバイダとして設定するには、「Webサービス・プロバイダベース・エンドポイント(WSDLから始める場合)」を参照してください。

同期プロバイダベース・エンドポイントの開発

javax.xml.ws.Provider<T>を使用して実装されるWebサービス・プロバイダベース・エンドポイントでは、JAXBバインディングを使用せずXMLメッセージ・レベルでコンテンツに直接アクセスできます。Providerインタフェースはメッセージを同期的に処理するため、サービスはレスポンス処理を待機し、その後処理を続行します。javax.xml.ws.Provider<T>インタフェースの詳細は、http://docs.oracle.com/javaee/6/api/javax/xml/ws/Provider.htmlを参照してください。

次の手順では、同期Webサービス・プロバイダベース・エンドポイントを実装するJWSファイルをプログラミングするための一般的な手順を説明します。

表24-3 同期Webサービス・プロバイダベース・エンドポイントを開発する手順

#

手順

説明

1

Webサービス・プロバイダベースJWSファイルで使用するJWSアノテーションをインポートします。

Webサービス・プロバイダベースJWSファイルの標準JWSアノテーションの内容は次のとおりです。

import javax.xml.ws.Provider;
import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.ServiceMode;

必要に応じて、追加のアノテーションをインポートします。サポートされているJWSアノテーションの完全なリストについては、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスのアノテーション・サポートに関する項を参照してください。

2

プロバイダベースの実装クラスを開発するときは、表24-2に定義されている、サポート対象のメッセージ・フォーマットの1つを指定します。

「メッセージ・フォーマットの指定」を参照してください。

3

必須の標準@WebServiceProvider JWSアノテーションをクラス・レベルで追加して、JavaクラスがWebサービス・プロバイダを公開することを指定します。

「JWSファイルによるWebサービス・プロバイダの実装の指定(@WebServiceProviderアノテーション)」を参照してください。

4

標準@ServiceMode JWSアノテーションをクラス・レベルで追加して、Webサービス・プロバイダがメッセージ・レベルまたはメッセージ・ペイロード・レベルで情報にアクセスすることを指定します。(オプション)

「使用モードの指定(@ServiceModeアノテーション)」を参照してください。

サービス・モードのデフォルトはService.Mode.Payloadです。

5

invoke()メソッドを定義します。

invoke()メソッドは呼び出されると、指定のメッセージ・フォーマットを使用するメソッドにメッセージまたはメッセージ・ペイロードを入力として提供します。「同期プロバイダベース・エンドポイントのinvoke()メソッドの定義」を参照してください。

次のJWSファイルのサンプルでは、簡単な同期Webサービス・プロバイダベース・エンドポイントの実装方法を示します。同期Webサービス・プロバイダベース・エンドポイントの開発手順の詳細は後の項で説明します。サンプル全体の中でこのJWSファイルを確認するには、Oracle WebLogic Serverに含まれるWebサービス・サンプルのJava EEのためのJAX-WS Webサービスの作成に関する項を参照してください。

注意:
RESTfulなWebサービスは、XML/HTTPバインディングのプロバイダベース・エンドポイントを使用して構築できます。RESTfulなWebサービスでのプロバイダベース・エンドポイントのプログラミング例は、「XML over HTTPを使用するWebサービスのプログラミング」を参照してください。

例24-1 同期プロバイダベース・エンドポイントを実装するJWSファイルの例

package examples.webservices.jaxws;

import org.w3c.dom.Node;

import javax.xml.transform.Source;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.Transformer;
import javax.xml.transform.dom.DOMResult;
import javax.xml.transform.stream.StreamSource;
import javax.xml.ws.Provider;
import javax.xml.ws.ServiceMode;
import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.Service;
import java.io.ByteArrayInputStream;

/**
* A simple Provider-based web service implementation.
*
* @author Copyright (c) 2010, Oracle and/or its affiliates.
* All Rights Reserved.
*/
// The @ServiceMode annotation specifies whether the Provider instance
// receives entire messages or message payloads.
@ServiceMode(value = Service.Mode.PAYLOAD)

// Standard JWS annotation that configures the Provider-based web service.
@WebServiceProvider(portName = "SimpleClientPort",
serviceName = "SimpleClientService",
targetNamespace = "http://jaxws.webservices.examples/",
wsdlLocation = "SimpleClientService.wsdl")
public class SimpleClientProviderImpl implements Provider<Source> {

//Invokes an operation according to the contents of the request message.
public Source invoke(Source source) {
try {
DOMResult dom = new DOMResult();
Transformer trans = TransformerFactory.newInstance().newTransformer();
trans.transform(source, dom);
Node node = dom.getNode();
// Get the operation name node.
Node root = node.getFirstChild();
// Get the parameter node.
Node first = root.getFirstChild();
String input = first.getFirstChild().getNodeValue();
// Get the operation name.
String op = root.getLocalName();
if ("invokeNoTransaction".equals(op)) {
return sendSource(input);
} else {
return sendSource2(input);
}
}
catch (Exception e) {
throw new RuntimeException("Error in provider endpoint", e);
}
}

private Source sendSource(String input) {
String body =
"<ns:invokeNoTransactionResponse
xmlns:ns=\"http://jaxws.webservices.examples/\"><return>"
+ "constructed:" + input
+ "</return></ns:invokeNoTransactionResponse>";
Source source = new StreamSource(new ByteArrayInputStream(body.getBytes()));
return source;
}

private Source sendSource2(String input) {
String body =
"<ns:invokeTransactionResponse
xmlns:ns=\"http://jaxws.webservices.examples/\"><return>"
+ "constructed:" + input
+ "</return></ns:invokeTransactionResponse>";
Source source = new StreamSource(new ByteArrayInputStream(body.getBytes()));
return source;
}

}

非同期プロバイダベース・エンドポイントの開発

Providerインタフェースを使用する場合と同様に、com.sun.xml.ws.api.server.AsyncProvider<T>インタフェースを使用して実装されるWebサービス・プロバイダベース・エンドポイントでは、JAXBバインディングを使用せずXMLメッセージ・レベルでコンテンツに直接アクセスできます。ただし、AsyncProviderインタフェースはメッセージを非同期に処理します。そのため、サービスはスレッドをブロックすることなく処理を続行し、リクエストが使用可能になった時点でそのリクエストを処理できます。

次の手順では、非同期Webサービス・プロバイダベース・エンドポイントを実装するJWSファイルをプログラミングするための一般的な手順を説明します。

表24-4 非同期Webサービス・プロバイダベース・エンドポイントを開発する手順

#

手順

説明

1

Webサービス・プロバイダベースJWSファイルで使用するJWSアノテーションをインポートします。

非同期Webサービス・プロバイダベースJWSファイルの標準JWSアノテーションの内容は次のとおりです。

import com.sun.xml.ws.api.server.AsyncProvider;
import com.sun.xml.ws.api.server.AsyncProviderCallback;
import javax.xml.ws.ServiceMode;

必要に応じて、追加のアノテーションをインポートします。サポートされているJWSアノテーションの完全なリストについては、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスのアノテーション・サポートに関する項を参照してください。

2

プロバイダベースの実装クラスを開発するときは、表24-2に定義されている、サポート対象のメッセージ・フォーマットの1つを指定します。

「メッセージ・フォーマットの指定」を参照してください。

3

必須の標準@WebServiceProvider JWSアノテーションをクラス・レベルで追加して、JavaクラスがWebサービス・プロバイダを公開することを指定します。

「JWSファイルによるWebサービス・プロバイダの実装の指定(@WebServiceProviderアノテーション)」を参照してください。

4

標準@ServiceMode JWSアノテーションをクラス・レベルで追加して、Webサービス・プロバイダがメッセージ・レベルまたはメッセージ・ペイロード・レベルで情報にアクセスすることを指定します。(オプション)

「使用モードの指定(@ServiceModeアノテーション)」を参照してください。

サービス・モードのデフォルトはService.Mode.Payloadです。

5

invoke()メソッドを定義します。

invoke()メソッドは呼び出されると、指定のメッセージ・フォーマットを使用するメソッドにメッセージまたはメッセージ・ペイロードを入力として提供します。「非同期プロバイダベース・エンドポイントのinvoke()メソッドの定義」を参照してください。

6

レスポンスを処理するための非同期ハンドラのコールバック・メソッドを定義します。

このメソッドは、レスポンスが返されたときにそのレスポンスを処理します。「非同期プロバイダベース・エンドポイントのコールバック・ハンドラの定義」を参照してください。

次のJWSファイルのサンプルでは、簡単な非同期Webサービス・プロバイダベース・エンドポイントの実装方法を示します。非同期Webサービス・プロバイダベース・エンドポイントの開発手順の詳細は後の項で説明します。

例24-2 非同期プロバイダベース・エンドポイントを実装するJWSファイルの例

package asyncprovider.server;

import com.sun.xml.ws.api.server.AsyncProvider;
import com.sun.xml.ws.api.server.AsyncProviderCallback;

import javax.xml.bind.JAXBContext;
import javax.xml.transform.Source;
import javax.xml.transform.stream.StreamSource;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.WebServiceException;
import javax.xml.ws.WebServiceProvider;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;

@WebServiceProvider(
wsdlLocation="WEB-INF/wsdl/hello_literal.wsdl",
targetNamespace = "urn:test",
serviceName="Hello")

public class HelloAsyncImpl implements AsyncProvider<Source> {

private static final JAXBContext jaxbContext = createJAXBContext();
private int bodyIndex;

public javax.xml.bind.JAXBContext getJAXBContext(){
return jaxbContext;
}

private static javax.xml.bind.JAXBContext createJAXBContext(){
try{
return javax.xml.bind.JAXBContext.newInstance(ObjectFactory.class);
}catch(javax.xml.bind.JAXBException e){
throw new WebServiceException(e.getMessage(), e);
}
}

private Source sendSource() {
System.out.println("**** sendSource ******");

String[] body  = {
"<HelloResponse xmlns=\"urn:test:types\">
<argument xmlns=\"\">foo</argument>
<extra xmlns=\"\">bar</extra>
</HelloResponse>",
"<ans1:HelloResponse xmlns:ans1=\"urn:test:types\">
<argument>foo</argument>
<extra>bar</extra>
</ans1:HelloResponse>",
};
int i = (++bodyIndex)%body.length;
return new StreamSource(
new ByteArrayInputStream(body[i].getBytes()));
}

private Hello_Type recvBean(Source source) throws Exception {
System.out.println("**** recvBean ******");
return (Hello_Type)jaxbContext.createUnmarshaller().unmarshal(source);
}

private Source sendBean() throws Exception {
System.out.println("**** sendBean ******");
HelloResponse resp = new HelloResponse();
resp.setArgument("foo");
resp.setExtra("bar");
ByteArrayOutputStream bout = new ByteArrayOutputStream();
jaxbContext.createMarshaller().marshal(resp, bout);
return new StreamSource(new ByteArrayInputStream(bout.toByteArray()));
}

public void invoke(Source source, AsyncProviderCallback<Source> cbak,
WebServiceContext ctxt) {
System.out.println("**** Received in AsyncProvider Impl ******");
try {
Hello_Type hello = recvBean(source);
String arg = hello.getArgument();
if (arg.equals("sync")) {
String extra = hello.getExtra();
if (extra.equals("source")) {
cbak.send(sendSource());
} else if (extra.equals("bean")) {
cbak.send(sendBean());
} else {
throw new WebServiceException("Expected extra =
(source|bean|fault), Got="+extra);
}
} else if (arg.equals("async")) {
new Thread(new RequestHandler(cbak, hello)).start();
} else {
throw new WebServiceException("Expected Argument =
(sync|async), Got="+arg);
}
} catch(Exception e) {
throw new WebServiceException("Endpoint failed", e);
}
}

private class RequestHandler implements Runnable {
final AsyncProviderCallback<Source> cbak;
final Hello_Type hello;
public RequestHandler(AsyncProviderCallback<Source> cbak, Hello_Type hello) {
this.cbak = cbak;
this.hello = hello;
}

public void run() {
try {
Thread.sleep(5000);
} catch(InterruptedException ie) {
cbak.sendError(new WebServiceException("Interrupted..."));
return;
}
try {
String extra = hello.getExtra();
if (extra.equals("source")) {
cbak.send(sendSource());
} else if (extra.equals("bean")) {
cbak.send(sendBean());
} else {
cbak.sendError(new WebServiceException(
"Expected extra = (source|bean|fault), Got="+extra));
}
} catch(Exception e) {
cbak.sendError(new WebServiceException(e));
}
}
}
}

メッセージ・フォーマットの指定

プロバイダベースの実装クラスを開発するときは、表24-2に定義されている、サポート対象のメッセージ・フォーマットの1つを指定します。

たとえば、例24-1「同期プロバイダベース・エンドポイントを実装するJWSファイルの例」に示したProviderの実装例では、SimpleClientProviderImplクラスがProvider<Source>インタフェースを実装し、入力と出力の両方の型がjava.xml.transform.Sourceオブジェクトであることを示しています。

public class SimpleClientProviderImpl implements Provider<Source> {
. . .
}

同様に、例24-2「非同期プロバイダベース・エンドポイントを実装するJWSファイルの例」に示したAsyncProviderの実装例では、HelloAsyncImplクラスがAsyncProvider<Source>インタフェースを実装し、入力と出力の両方の型がjava.xml.transform.Sourceオブジェクトであることを示しています。

public class HelloAsyncImpl implements AsyncProvider<Source>  {
. . .
}

JWSファイルによるWebサービス・プロバイダの実装の指定(@WebServiceProviderアノテーション)

次のコードの抜粋のように、標準のjavax.xml.ws.WebServiceProviderアノテーションを使用して、JWSファイルがWebサービス・プロバイダを実装することをクラス・レベルで指定します。

@WebServiceProvider(portName = "SimpleClientPort",
serviceName = "SimpleClientService",
targetNamespace = "http://jaxws.webservices.examples/",
wsdlLocation = "SimpleClientService.wsdl")

この例では、サービス名はSimpleClientServiceであり、生成されるWSDLファイルのwsdl:service要素にマップされます。ポート名はSimpleClientPortであり、生成されるWSDLファイルのwsdl:port要素にマップされます。生成されるWSDLで使用されるターゲット・ネームスペースはhttp://jaxws.webservices.examples/で、WSDLの場所はWebサービス・プロバイダに対して局所的であり、SimpleClientService.wsdlにあります。

@WebServiceProviderアノテーションの詳細は、https://jax-ws.java.net/nonav/2.1.5/docs/annotations.htmlを参照してください。

使用モードの指定(@ServiceModeアノテーション)

javax.xml.ws.ServiceModeアノテーションを使用して、Webサービス・プロバイダベース・エンドポイントが、メッセージ全体を受信するか(Service.Mode.MESSAGE)、メッセージ・ペイロードのみを受信するか(Service.Mode.PAYLOAD)を指定します。

例:

@ServiceMode(value = Service.Mode.PAYLOAD)

指定しない場合、@ServiceModeアノテーションのデフォルトはService.Mode.PAYLOADです。

有効なメッセージ・フォーマットと使用モードの組合せのリストは、表24-2を参照してください。

@ServiceModeアノテーションの詳細は、https://jax-ws.java.net/nonav/2.1.4/docs/annotations.htmlを参照してください。

同期プロバイダベース・エンドポイントのinvoke()メソッドの定義

Provider<T>インタフェースによって、実装クラスに定義する必要がある1つのメソッドが定義されます。

T invoke(T request)

Webサービス・リクエストが受信されると、invoke()メソッドが呼び出され、指定のメッセージ・フォーマットを使用するメソッドにメッセージまたはメッセージ・ペイロードを入力として提供します。

たとえば、「同期プロバイダベース・エンドポイントを実装するJWSファイルの例」のProviderの実装例では、次の抜粋に示すように、invokeメソッドの入力としてSourceパラメータを受け取り、Sourceレスポンスを返すようにクラスが定義されています。

public Source invoke(Source source) {
try {
DOMResult dom = new DOMResult();
Transformer trans = TransformerFactory.newInstance().newTransformer();
trans.transform(source, dom);
Node node = dom.getNode();
// Get the operation name node.
Node root = node.getFirstChild();
// Get the parameter node.
Node first = root.getFirstChild();
String input = first.getFirstChild().getNodeValue();
// Get the operation name.
String op = root.getLocalName();
if ("invokeNoTransaction".equals(op)) {
return sendSource(input);
} else {
return sendSource2(input);
}
}
catch (Exception e) {
throw new RuntimeException("Error in provider endpoint", e);
}
}

非同期プロバイダベース・エンドポイントのinvoke()メソッドの定義

AsycnProvider<T>インタフェースによって、実装クラスに定義する必要がある1つのメソッドが定義されます。

void invoke(T request, AsyncProviderCallback<t> callback, WebserviceContext context))

メソッドを呼び出すには、次のパラメータを渡します。

- 指定のフォーマットのリクエスト・メッセージまたはメッセージ・ペイロード。

- レスポンスが返されたときにそのレスポンスを処理するcom.sun.xml.ws.api.server.AsyncProviderCallback実装。詳細は、「非同期プロバイダベース・エンドポイントのコールバック・ハンドラの定義」を参照してください。

- 処理されるリクエストのメッセージ・コンテキストを定義するjavax.xml.ws.WebServiceContext。非同期プロバイダベース・エンドポイントでは、注入されたWebServiceContextは使用できません。これは、情報を返す必要のあるリクエストを判別する際に呼び出し側スレッドに依存するためです。かわりに、WebServiceContextオブジェクトを渡します。このオブジェクトは、AsyncProviderCallbackを呼び出すまで使用できます。

たとえば、例24-2「非同期プロバイダベース・エンドポイントを実装するJWSファイルの例」のAysncProviderの実装例では、次の抜粋に示すように、このクラスのinvokeメソッドが次のように定義されています。

public void invoke(Source source, AsyncProviderCallback<Source> cbak,
WebServiceContext ctxt) {
System.out.println("**** Received in AsyncProvider Impl ******");
try {
Hello_Type hello = recvBean(source);
String arg = hello.getArgument();
if (arg.equals("sync")) {
String extra = hello.getExtra();
if (extra.equals("source")) {
cbak.send(sendSource());
} else if (extra.equals("bean")) {
cbak.send(sendBean());
} else {
throw new WebServiceException("Expected extra =
(source|bean|fault), Got="+extra);
}
} else if (arg.equals("async")) {
new Thread(new RequestHandler(cbak, hello)).start();
} else {
throw new WebServiceException("Expected Argument =
(sync|async), Got="+arg);
}
} catch(Exception e) {
throw new WebServiceException("Endpoint failed", e);
}
}

非同期プロバイダベース・エンドポイントのコールバック・ハンドラの定義

AsyncProviderCallbackインタフェースには、非同期レスポンスを受信したときにそのレスポンスを処理するためのコールバック・ハンドラを定義できます。

たとえば、例24-2「非同期プロバイダベース・エンドポイントを実装するJWSファイルの例」から抜粋した次のAysncProviderの実装例では、RequestHandlerメソッドでAsyncProviderCallbackコールバック・ハンドラを使用して非同期レスポンスを処理しています。

private class RequestHandler implements Runnable {
final AsyncProviderCallback<Source> cbak;
final Hello_Type hello;
public RequestHandler(AsyncProviderCallback<Source> cbak, Hello_Type hello) {
this.cbak = cbak;
this.hello = hello;
}

public void run() {
try {
Thread.sleep(5000);
} catch(InterruptedException ie) {
cbak.sendError(new WebServiceException("Interrupted..."));
return;
}
try {
String extra = hello.getExtra();
if (extra.equals("source")) {
cbak.send(sendSource());
} else if (extra.equals("bean")) {
cbak.send(sendBean());
} else {
cbak.sendError(new WebServiceException(
"Expected extra = (source|bean|fault), Got="+extra));
}
} catch(Exception e) {
cbak.sendError(new WebServiceException(e));
}
}
}
}

Webサービス・プロバイダベース・エンドポイントの開発(WSDLから始める場合)

プロバイダベース・エンドポイントがWSDLファイルから生成される場合、<provider> WSDL拡張を使用してポートをプロバイダとしてマークできます。例:

<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<bindings wsdlLocation="SimpleClientService.wsdl"
xmlns="http://java.sun.com/xml/ns/jaxws">
<bindings node="wsdl:definitions" >
<package name="provider.server"/>
<provider>true</provider>
</bindings>

プロバイダベース・エンドポイントでのSOAPハンドラの使用

プロバイダベース・エンドポイントは、メッセージのリクエストやレスポンスの追加処理において、SOAPメッセージにアクセスしなければならないときがあります。SEIベース・エンドポイントに実行する場合と同様に、SOAPメッセージ・ハンドラを作成し、プロバイダベース・エンドポイントがSOAPメッセージに対してこの追加処理を実行できるようにすることができます。SOAPハンドラの作成に関する詳細は、「SOAPメッセージ・ハンドラの作成」を参照してください。

表18-1「WebサービスへのSOAPメッセージ・ハンドラの追加手順」には、WebサービスにSOAPハンドラを追加する場合に必要な手順が順に記載されています。これらの手順は、Webサービス・プロバイダベース・エンドポイントにも適用できます。

例:

1. SOAPメッセージ・ハンドラを設計し、それらを1つのハンドラ・チェーンにグループ化します(「SOAPメッセージ・ハンドラおよびハンドラ・チェーンの設計」を参照)。

2. ハンドラ・チェーン内のハンドラごとに、SOAPメッセージ・ハンドラ・インタフェースを実装するJavaクラスを作成します(「SOAPメッセージ・ハンドラの作成」を参照)。
SOAPハンドラの例、MyHandlerを次に示します。

package provider.rootpart_charset_772.server;

import javax.activation.DataHandler;
import javax.activation.DataSource;
import javax.xml.namespace.QName;
import javax.xml.soap.AttachmentPart;
import javax.xml.soap.SOAPMessage;
import javax.xml.ws.WebServiceException;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.handler.soap.SOAPHandler;
import javax.xml.ws.handler.soap.SOAPMessageContext;
import java.io.InputStream;
import java.io.OutputStream;.import java.io.ByteArrayInputStream;
import java.util.Set;

public class MyHandler implements SOAPHandler<SOAPMessageContext> {

public Set<QName> getHeaders() {
return null;
}

public boolean handleMessage(SOAPMessageContext smc) {
if (!(Boolean)smc.get(MessageContext.MESSAGE_OUTBOUND_PROPERTY))
return true;
try {
SOAPMessage msg = smc.getMessage();
AttachmentPart part = msg.createAttachmentPart(getDataHandler());
part.setContentId("SOAPTestHandler@example.jaxws.sun.com");
msg.addAttachmentPart(part);
msg.saveChanges();
smc.setMessage(msg);
} catch (Exception e) {
throw new WebServiceException(e);
}
return true;
}

public boolean handleFault(SOAPMessageContext context) {
return true;
}

public void close(MessageContext context) {}

private DataHandler getDataHandler() throws Exception {
return new DataHandler(new DataSource() {
public String getContentType() {
return "text/xml";
}

public InputStream getInputStream() {
return new ByteArrayInputStream("<a/>".getBytes());
}

public String getName() {
return null;
}

public OutputStream getOutputStream() {
throw new UnsupportedOperationException();
}
});
}
}

3. @javax.jws.HandlerChainアノテーションをProvider実装に追加します(「JWSファイルでのハンドラ・チェーンの構成」を参照)。
例:

package provider.rootpart_charset_772.server;

import javax.jws.HandlerChain;
import javax.xml.soap.MessageFactory;
import javax.xml.soap.SOAPMessage;
import javax.xml.transform.Source;
import javax.xml.transform.stream.StreamSource;
import javax.xml.ws.*;
import java.io.ByteArrayInputStream;

@WebServiceProvider(targetNamespace="urn:test", portName="HelloPort", serviceName="Hello")
@ServiceMode(value=Service.Mode.MESSAGE)
@HandlerChain(file="handlers.xml")
public class SOAPMsgProvider implements Provider<SOAPMessage> {

public SOAPMessage invoke(SOAPMessage msg) {
try {
// keeping white space in the string is intentional
String content = "<soapenv:Envelope
xmlns:soapenv=\"http://schemas.xmlsoap.org/soap/envelope/\">
<soapenv:Body>  <VoidTestResponse
xmlns=\"urn:test:types\">
</VoidTestResponse></soapenv:Body></soapenv:Envelope>";
Source source = new StreamSource(new
ByteArrayInputStream(content.getBytes()));
MessageFactory fact = MessageFactory.newInstance();
SOAPMessage soap = fact.createMessage();
soap.getSOAPPart().setContent(source);
soap.getMimeHeaders().addHeader("foo", "bar");
return soap;
} catch(Exception e) {
throw new WebServiceException(e);
}
}
}

4. ハンドラ・チェーン構成ファイルを作成します(「ハンドラ・チェーン構成ファイルの作成」を参照)。
ハンドラ・チェーン構成ファイルの例(handlers.xml)を次に示します。

<handler-chains xmlns='http://java.sun.com/xml/ns/javaee'>
<handler-chain>
<handler>
<handler-name>MyHandler</handler-name>
<handler-class>
provider.rootpart_charset_772.server.MyHandler
</handler-class>
</handler>
</handler-chain>
</handler-chains>

5. ハンドラ・チェーン内のすべてのハンドラ・クラスをコンパイルし、Webサービスを再ビルドします(「Webサービスのコンパイルと再ビルド」を参照)。

Webサービス・ディスパッチ・クライアントの開発

javax.xml.ws.Dispatch<T>インタフェースを使用して実装されるWebサービス・ディスパッチ・クライアントでは、クライアントがXMLレベルでメッセージを処理できます。

次の手順では、Webサービス・ディスパッチ・クライアントをプログラミングするための一般的な手順を説明します。

表24-5 Webサービス・プロバイダベース・エンドポイントを開発する手順

#

手順

説明

1

Webサービス・プロバイダベースJWSファイルで使用するJWSアノテーションをインポートします。

Webサービス・プロバイダベースJWSファイルの標準JWSアノテーションの内容は次のとおりです。

import javax.xml.ws.Service;
import javax.xml.ws.Dispatch;
import javax.xml.ws.ServiceMode;

必要に応じて、追加のアノテーションをインポートします。サポートされているJWSアノテーションの完全なリストについては、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスのアノテーション・サポートに関する項を参照してください。

2

Dispatchインスタンスを作成します。

「ディスパッチ・インスタンスの作成」を参照してください。

3

Webサービス操作を呼び出します。

Webサービス操作は、同期(一方向または双方向)または非同期(ポーリングまたは非同期ハンドラ)で呼び出すことができます。「Webサービス操作の呼出し」を参照してください。

Webサービス・ディスパッチ・クライアントの例

次のサンプルは、基本的なWebサービス・ディスパッチ・クライアントがどのように実装されるかを示します。このサンプルの詳細は後の項で説明します。

例24-3 Webサービス・ディスパッチ・クライアントの例

package jaxws.dispatch.client;

import java.io.ByteArrayOutputStream;
import java.io.OutputStream;
import java.io.StringReader;
import java.net.URL;

import javax.xml.soap.SOAPException;
import javax.xml.soap.SOAPMessage;
import javax.xml.transform.OutputKeys;
import javax.xml.transform.Source;
import javax.xml.transform.Transformer;
import javax.xml.transform.TransformerException;
import javax.xml.transform.TransformerFactory;
import javax.xml.transform.stream.StreamResult;
import javax.xml.transform.stream.StreamSource;

import javax.xml.ws.Dispatch;
import javax.xml.ws.Service;
import javax.xml.ws.WebServiceException;
import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBElement;
import javax.xml.namespace.QName;
import javax.xml.ws.soap.SOAPBinding;

public class WebTest extends TestCase {
private static String in_str = "wiseking";
private static String request =
"<ns1:sayHello xmlns:ns1=\"http://example.org\"><arg0>"+in_str+"</arg0></ns1:sayHello>";

private static final QName portQName = new QName("http://example.org", "SimplePort");
private Service service = null;

protected void setUp() throws Exception {

String url_str = System.getProperty("wsdl");
URL url = new URL(url_str);
QName serviceName = new QName("http://example.org", "SimpleImplService");
service = Service.create(serviceName);
service.addPort(portQName, SOAPBinding.SOAP11HTTP_BINDING, url_str);
System.out.println("Setup complete.");

}

public void testSayHelloSource() throws Exception {
setUp();
Dispatch<Source> sourceDispatch =
service.createDispatch(portQName, Source.class, Service.Mode.PAYLOAD);
System.out.println("\nInvoking xml request: " + request);
Source result = sourceDispatch.invoke(new StreamSource(new StringReader(request)));
String xmlResult = sourceToXMLString(result);
System.out.println("Received xml response: " + xmlResult);
assertTrue(xmlResult.indexOf("HELLO:"+in_str)>=0);
}

private String sourceToXMLString(Source result) {
String xmlResult = null;
try {
TransformerFactory factory = TransformerFactory.newInstance();
Transformer transformer = factory.newTransformer();
transformer.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");
transformer.setOutputProperty(OutputKeys.METHOD, "xml");
OutputStream out = new ByteArrayOutputStream();
StreamResult streamResult = new StreamResult();
streamResult.setOutputStream(out);
transformer.transform(result, streamResult);
xmlResult = streamResult.getOutputStream().toString();
} catch (TransformerException e) {
e.printStackTrace();
}
return xmlResult;
}

}

ディスパッチ・インスタンスの作成

javax.xml.ws.Serviceインタフェースは、Dispatchインスタンスの作成でファクトリとして機能します。ディスパッチ・インスタンスを作成するには、まずServiceインスタンスを作成する必要があります。その後、Service.createDispatch()メソッドを使用してディスパッチ・インスタンスを作成します。

次のパラメータから1つ以上のパラメータをcreateDispatch()メソッドに渡すことができます。

- ターゲット・サービス・エンドポイントの修飾された名前(QName)またはエンドポイント参照。

- タイプ・パラメータTのクラス。この例では、javax.xml.transform.Sourceフォーマットが使用されます。有効な値は、表24-2を参照してください。

- 使用モード。この例では、メッセージ・ペイロードが指定されます。有効な使用モードは、表24-1を参照してください。

- プロキシで構成するWebサービス機能のリスト。

- メッセージまたはメッセージ・ペイロードのマーシャルまたはアンマーシャルに使用されるJAXBコンテキスト。

Service.createDispatch()メソッドの呼出しに使用できる有効なパラメータの詳細は、Javadocの「javax.xml.ws.Service」(https://jax-ws.java.net/nonav/2.1.1/docs/api/javax/xml/ws/Service.html)を参照してください。

例:

...
String url_str = System.getProperty("wsdl");
QName serviceName = new QName("http://example.org", "SimpleImplService");
service = Service.create(serviceName);
service.addPort(portQName, SOAPBinding.SOAP11HTTP_BINDING, url_str);
Dispatch<Source> sourceDispatch =
service.createDispatch(portQName, Source.class, Service.Mode.PAYLOAD);
...

前の例では、createDispatch()メソッドは次の3つのパラメータを取ります。

- ターゲット・サービス・エンドポイントの修飾された名前(QName)。

- タイプ・パラメータTのクラス。この例では、javax.xml.transform.Sourceフォーマットが使用されます。有効な値は、表24-2を参照してください。

- 使用モード。この例では、メッセージ・ペイロードが指定されます。有効な使用モードは、表24-1を参照してください。

次の例では、Webサービス機能のリストを渡す方法を示します。具体的には、非同期クライアント・トランスポート機能と非同期クライアント・ハンドラ機能を渡します。これらの機能の詳細は、第12章「非同期クライアントの開発」を参照してください。

...
protected Dispatch createDispatch(boolean isSoap12, Class dateType,
Service.Mode mode, AsyncClientHandlerFeature feature)
throws Exception {
String address = publishEndpoint(isSoap12);
Service service = Service.create(new URL(address + "?wsdl"),
new QName("http://example.org", "AddNumbersService"));
QName portName = new QName("http://example.org", "AddNumbersPort");
AsyncClientTransportFeature transportFeature = new
AsyncClientTransportFeature("http://localhost:8238/clientsoap12/" +
UUID.randomUUID().toString());
Dispatch dispatch = service.createDispatch(portName, dateType, mode,
feature, transportFeature);
return dispatch;
}
...

Webサービス操作の呼出し

Dispatchインスタンスが作成されたら、それを使用してWebサービス操作を呼び出します。Webサービス操作は、同期(一方向または双方向)または非同期(ポーリングまたは非同期ハンドラ)で呼び出すことができます。同期および非同期の呼出し方法の詳細は、Javadocの「javax.xml.ws.Dispatch」(https://jax-ws.java.net/nonav/2.1.1/docs/api/javax/xml/ws/Dispatch.html)を参照してください。

たとえば、次のコードの抜粋では、XMLメッセージはjavax.xml.transform.stream.StreamSourceオブジェクトとしてカプセル化され、同期invoke()メソッドに渡されています。レスポンスXMLはresult変数でSourceオブジェクトとして返され、XMLに変換されます。メッセージをXMLに戻すために使用されるsourcetoXMLString()メソッドは、例24-3に示しています。

...
private static String request = "<ns1:sayHello xmlns:ns1=\"http://example.org\"><arg0>"+in_str+"</arg0></ns1:sayHello>";
Source result = sourceDispatch.invoke(new StreamSource(new StringReader(request)));
String xmlResult = sourceToXMLString(result);
...

25 SOAPヘッダーの送受信

この章では、com.sun.xml.ws.developer.WSBindingProviderで利用可能なメソッドを使用して、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスで、送信または受信SOAPヘッダーを送信する方法を説明します。

この章の内容は次のとおりです:

- SOAPヘッダーの送受信の概要

- WSBindingProviderを使用したSOAPヘッダーの送信

- WSBindingProviderを使用したSOAPヘッダーの受信

注意:
com.sun.xml.ws.developer.WSBindingProvider APIおよびcom.sun.xml.ws.api.message.Headers APIは、JDK 6.0の拡張としてサポートされています。これらのAPIはJDK 6.0キットの一部としては提供されないため、変更される可能性があります。

SOAPヘッダーの送受信の概要

プロキシまたはディスパッチ・クライアントを作成すると、そのクライアントにより、javax.xml.ws.BindingProviderインタフェースが実装されます。SOAPヘッダーを送信または受信する必要がある場合には、Webサービス・プロキシ・クライアントまたはディスパッチ・クライアントをcom.sun.xml.ws.developer.WSBindingProviderにダウンキャストし、インタフェースのメソッドを使用することで、アウトバウンドSOAPヘッダーの送信やインバウンドSOAPヘッダーの受信を行うことができます。

WSBindingProviderを使用したSOAPヘッダーの送信

com.sun.xml.ws.developer.WSBindingProviderに対してsetOutboundHeadersメソッドを使用し、SOAPヘッダーを送信します。SOAPヘッダーの作成にはcom.sun.xml.ws.api.message.Headersメソッドを使用します。

たとえば、次のコードの抜粋は、簡単な文字列値をヘッダーとして渡す方法を示しています。

例25-1 WSBindingProviderを使用したSOAPヘッダーの送信

import com.sun.xml.ws.developer.WSBindingProvider;
import com.sun.xml.ws.api.message.Headers;
import javax.xml.namespace.QName;
...
HelloService helloService = new HelloService();
HelloPort port = helloService.getHelloPort();
WSBindingProvider bp = (WSBindingProvider)port;

bp.setOutboundHeaders(
// Sets a simple string value as a header
Headers.create(new QName("simpleHeader"),"stringValue")
);
...

WSBindingProviderを使用したSOAPヘッダーの受信

com.sun.xml.ws.developer.WSBindingProviderに対してgetInboundHeadersメソッドを使用し、SOAPヘッダーを受信します。

たとえば、次のコードの抜粋は、インバウンド・ヘッダーを取得する方法を示しています。

例25-2 WSBindingProviderを使用したSOAPヘッダーの受信

import com.sun.xml.ws.developer.WSBindingProvider;
import com.sun.xml.ws.api.message.Headers;
import javax.xml.namespace.QName;
import java.util.List;
...
HelloService helloService = new HelloService();
HelloPort port = helloService.getHelloPort();
WSBindingProvider bp = (WSBindingProvider)port;

List inboundHeaders = bp.getInboundHeaders();
...

26 コールバックの使用

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスで、コールバックを使用してクライアントにイベントを通知する方法について説明します。

この章の内容は次のとおりです:

- コールバックの概要

- コールバック実装のサンプル

- コールバックのプログラミング手順

- ターゲットWebサービスのプログラミングのガイドライン

- コールバック・クライアントWebサービスのプログラミングのガイドライン

- コールバックWebサービスのプログラミングのガイドライン

- ターゲットWebサービスのbuild.xmlファイルの更新

コールバックの概要

コールバックとは、クライアントとサービスの間の規約の1つです。サービスはコールバックを使用することで、クライアントに追加のデータを照会することを目的として、サービス・メソッドの呼出しの間にクライアント提供のエンドポイントで操作を呼び出すことができます。これにより、クライアントが動作を注入したり、クライアントに進行状況を通知したりすることが可能になります。サービスは、コールバックのポート・タイプを定義するWSDLを使用してコールバックの要件を公開します。一方クライアントは、WS-Addressingを使用して、コールバック・エンドポイントのアドレスをサービスに通知します。

コールバック実装のサンプル

この節で説明するコールバック実装のサンプルは、以下の3つのJavaファイルから構成されています。

- コールバックWebサービスを実装するJWSファイル: コールバックWebサービスには、コールバック・メソッドが定義されています。この実装からターゲットWebサービスに情報が返送され、最終的にクライアントWebサービスに返送されます。
この項で示すサンプルでは、コールバックWebサービスの名前をCallbackServiceとしています。このWebサービスには、単一のコールバック・メソッド、callback()が定義されています。

- ターゲットWebサービスを実装するJWSファイル: ターゲットWebサービスには、コールバックWebサービスに定義されたメソッドを呼び出す1つ以上の標準操作が含まれます。ターゲットWebサービス操作の呼出し元であるクライアントWebサービスには、ターゲットWebサービスからメッセージが返送されます。
例では、このWebサービスの名前がTargetServiceになっており、単一の標準メソッドtargetOperation()が定義されています。

- クライアントWebサービスを実装するJWSファイル: クライアントWebサービスは、ターゲットWebサービスの操作を呼び出します。多くの場合、このWebサービスには、コールバック・メソッドを介してターゲットWebサービスからコールバック・メッセージを受け取ったときにクライアントが実行すべき動作を指定する1つ以上のメソッドが含まれます。
サンプルでは、このWebサービスの名前をCallerServiceとしています。call()は、TargetServiceを標準の方法で呼び出すメソッドです。

次の図に、コールバック実装のサンプルでのメッセージの流れを示します。

図26-1 コールバック実装のサンプル

1. あるWebLogic Serverインスタンスで実行されているCallerService Webサービスのcall()メソッドが、TargetServiceのtargetOperation()メソッドを明示的に呼び出し、CallbackServiceにWebサービスのエンドポイントを渡します。通常、TargetServiceサービスは、別のWebLogic Serverインスタンスで実行されています。

2. TargetService.targetOperation()メソッドの実装が、CallbackServiceのcallback()メソッドを明示的に呼び出します。このメソッドは、呼び出されると、CallerServiceから渡されたWebサービス・エンドポイントを使用して、コールバック・サービスを実装します。

3. CallbackService.callback()メソッドが、TargetService Webサービスに情報を返送します。

4. 最終的に、TargetService.targetOperation()メソッドが情報をCallerServiceサービスに返送し、コールバック・シーケンスが完了します。

コールバックのプログラミング手順

この項の手順では、コールバックを実装するために必要な3つのJWSファイル(ターゲットWebサービス、クライアントWebサービス、コールバックWebサービス)をプログラミングおよびコンパイルする方法について説明します。この手順では、これらのJWSファイルをゼロから作成する方法を示しています。既存のJWSファイルを更新する場合は、この手順をガイドとして利用してください。

Antベースの開発環境を設定済であり、かつjwsc Antタスクを実行してWebサービスをデプロイするためのターゲットを追加できる、作業用のbuild.xmlファイルがあることが前提となっています。詳細は、第4章「JWSファイルのプログラミング」を参照してください。

表26-1 コールバックのプログラミング手順

#

手順

説明

1

ターゲットWebサービスを実装する、新しいJWSファイルを作成するか、既存のJWSファイルを更新します。

使い慣れたIDEまたはテキスト・エディタを使用します。「ターゲットWebサービスのプログラミングのガイドライン」を参照してください。

注意: ターゲットWebサービスを実装するJWSファイルは、コールバックWebサービスの1つ以上のコールバック・メソッドを呼び出します。ただし、コールバックWebサービスをプログラミングする手順については後ほど説明します。したがって、これらの3つのJWSファイルは、この手順に従って順番にプログラミングするのではなく、すべてを同時にプログラミングすることをお薦めします。手順をこの順番に説明しているのは、あくまで各手順を理解しやすくするためです。

2

build.xmlファイルを更新して、ターゲットJWSファイルをWebサービスにコンパイルするjwsc Antタスクの呼出しを含めます。

「ターゲットWebサービスのbuild.xmlファイルの更新」を参照してください。

3

Antターゲットを実行して、ターゲットWebサービスをビルドします。

例:

prompt> ant build-target

4

ターゲットWebサービスを通常どおりデプロイします。

第3章「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

5

クライアントWebサービスを実装する、新しいJWSファイルを作成するか、既存のJWSファイルを更新します。

クライアントWebサービスは、ターゲットWebサービスをホストするものとは別のWebLogic Serverインスタンスにデプロイされていることが前提となっています。「コールバック・クライアントWebサービスのプログラミングのガイドライン」を参照してください。

6

コールバックWebサービスを実装するJWSファイルを作成します。

「コールバックWebサービスのプログラミングのガイドライン」を参照してください。

7

クライアントWebサービスをビルドするbuild.xmlファイルを更新します。

クライアントWebサービスをビルドするjwsc Antタスクでは、CallbackWS.javaもコンパイルされます。また、そのクラス・ファイルは、Fileset Antタスク要素によってWARファイルに格納されます。例:

<clientgen
type="JAXWS"
wsdl="${awsdl}"
packageName="jaxws.callback.client.add"/>
<clientgen
type="JAXWS"
wsdl="${twsdl}"
packageName="jaxws.callback.client.target"/>
<FileSet dir="." >
<include name="CallbackWS.java" />
</FileSet>

8

Antターゲットを実行して、クライアントおよびコールバックWebサービスをビルドします。

例:

prompt> ant build-caller

9

クライアントWebサービスを通常どおりデプロイします。

第3章「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

ターゲットWebサービスのプログラミングのガイドライン

次のサンプルでは、ターゲットWebサービスを実装する簡単なJWSファイルを示します。太字で示されたJavaコードに対応するコーディングのガイドラインについては、サンプルの後の説明を参照してください。

package examples.webservices.callback;

import javax.jws.WebService;
import javax.xml.ws.BindingType;
import javax.xml.ws.wsaddressing.W3CEndpointReference;
import examples.webservices.callback.callbackservice.*;

@WebService(
portName="TargetPort",
serviceName="TargetService",
targetNamespace="http://example.oracle.com",
endpointInterface=
"examples.webservices.callback.target.TargetPortType",
wsdlLocation="/wsdls/Target.wsdl")
@BindingType(value="http://schemas.xmlsoap.org/wsdl/soap/http")

public class TargetImpl {
public String targetOperation(String s, W3CEndpointReference callback)
{
CallbackService aservice = new CallbackService();
CallbackPortType aport =
aservice.getPort(callback, CallbackPortType.class);
String result = aport.callback(s);
return result + " processed by target";
}
}

ターゲットWebサービスを実装するJWSファイルをプログラミングする際には、次のガイドラインに従います。ガイドラインのコード・スニペットは、前述のサンプルでは太字で示されています。

- コールバック・サービスのエンドポイントを渡すために必要なパッケージをインポートし、CallbackServiceスタブ実装にアクセスします。

import javax.xml.ws.wsaddressing.W3CEndpointReference;
import examples.webservices.callback.callbackservice.*;

- このスタブ実装を使用してCallbackService実装のインスタンスを作成し、呼出し側アプリケーション(CallerService)から渡されたCallbackServiceサービスのエンドポイントを渡すことでポートを取得します。

CallbackService aservice = new CallbackService();
CallbackPortType aport =
aservice.getPort(callback, CallbackPortType.class);

- インスタンス化したポートを使用して、CallbackServiceのコールバック操作を呼び出します。

String result = aport.callback(s);

- 結果をCallerServiceサービスに返します。

return result + " processed by target";

コールバック・クライアントWebサービスのプログラミングのガイドライン

次のサンプルでは、「ターゲットWebサービスのプログラミングのガイドライン」で説明したターゲットWebサービスを呼び出すクライアントWebサービス用の簡単なJWSファイルを示します。太字で示されたJavaコードに対応するコーディングのガイドラインについては、サンプルの後の説明を参照してください。

package examples.webservices.callback;

import javax.annotation.Resource;
import javax.jws.WebMethod;
import javax.jws.WebService;
import javax.xml.ws.BindingType;
import javax.xml.ws.Endpoint;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.WebServiceException;
import javax.xml.ws.WebServiceRef;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.wsaddressing.W3CEndpointReference;

import examples.webservices.callback.target.*;

@WebService(
portName="CallerPort",
serviceName="CallerService",
targetNamespace="http://example.oracle.com")
@BindingType(value="http://schemas.xmlsoap.org/wsdl/soap/http")

public class CallerImpl
{
@Resource
private WebServiceContext context;

@WebServiceRef()
private TargetService target;

@WebMethod()
public String call(String s) {
Object sc =
context.getMessageContext().get(MessageContext.SERVLET_CONTEXT);
Endpoint callbackImpl = Endpoint.create(new CallbackWS());
callbackImpl.publish(sc);
TargetPortType tPort = target.getTargetPort();
String result = tPort.targetOperation(s,
callbackImpl.getEndpointReference(W3CEndpointReference.class));
callbackImpl.stop();
return result;
}
}

ターゲットWebサービスを呼び出すJWSファイルをプログラミングする際には、次のガイドラインに従います。ガイドラインのコード・スニペットは、前述のサンプルでは太字で示されています。

- サーブレット・コンテキストにアクセスするために必要なパッケージをインポートし、WebサービスのエンドポイントをパブリッシュしてTargetServiceスタブ実装にアクセスします。

import javax.xml.ws.Endpoint;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.wsaddressing.W3CEndpointReference;
import examples.webservices.callback.target.*;

- WebServiceContextおよびMessageContextを使用してサーブレット・コンテキストを取得します。サーブレット・コンテキストは、後ほどWebサービスのエンドポイントをパブリッシュする際に使用します。

@Resource
private WebServiceContext context;
.
.
.
Object sc
context.getMessageContext().get(MessageContext.SERVLET_CONTEXT);

WebServiceContextおよびMessageContextを使用した実行時情報へのアクセスの詳細は、「Webサービスの実行時情報へのアクセス」を参照してください。

- CallbackService実装に渡すWebサービスのエンドポイントを作成し、受信したリクエストを受け入れるためにエンドポイントをパブリッシュします。

Endpoint callbackImpl = Endpoint.create(new CallbackWS());
callbackImpl.publish(sc);

Webサービスのパブリッシュの詳細は、第28章「Webサービスのエンドポイントのパブリッシュ」を参照してください。

- TargetServiceスタブ実装のインスタンスにアクセスし、インスタンス化したポートを使用してTargetServiceのtargetOperation操作を呼び出します。CallbackServiceサービスのエンドポイントは、javax.xml.ws.wsaddressing.W3CEndpointReferenceデータ型として渡します。

注意:
コールバックが到着する時間範囲内にコールバックWebサービスがデプロイされるようにしてください。

@WebServiceRef()
private TargetService target;
.
.
.
TargetPortType tPort = target.getTargetPort();
String result = tPort.targetOperation(s,
callbackImpl.getEndpointReference(W3CEndpointReference.class));

- エンドポイントのパブリッシュを停止します。

callbackImpl.stop();

コールバックWebサービスのプログラミングのガイドライン

次のサンプルでは、コールバックWebサービスを実装する簡単なJWSファイルを示します。callback操作は太字で示されています。

package examples.webservices.callback;

import javax.jws.WebService;
import javax.xml.ws.BindingType;

@WebService(
portName="CallbackPort",
serviceName="CallbackService",
targetNamespace="http://example.oracle.com",
endpointInterface=
"examples.webservices.callback.callbackservice.CallbackPortType",
wsdlLocation="/wsdls/Callback.wsdl")

@BindingType(value="http://schemas.xmlsoap.org/wsdl/soap/http")

public class CallbackWS implements
examples.webservices.callback.callbackservice.CallbackPortType {

public CallbackWS() {
}

public java.lang.String callback(java.lang.String arg0) {
return arg0.toUpperCase();
}
}

ターゲットWebサービスのbuild.xmlファイルの更新

build.xmlファイルを更新して、コールバックWebサービスを呼び出すターゲットWebサービスを生成するには、次のサンプルのようにtaskdefsおよびbuild-targetターゲットを追加します。詳細は、サンプルの後の説明を参照してください。

<taskdef name="jwsc"
classname="weblogic.wsee.tools.anttasks.JwscTask" />

<target name="build-target">
<jwsc srcdir="src" destdir="${ear-dir}" listfiles="true">
<jws file="TargetImpl.java"
compiledWsdl="${cowDir}/target/Target_wsdl.jar" type="JAXWS">
<WLHttpTransport contextPath="target" serviceUri="TargetService"/>
</jws>
<clientgen
type="JAXWS"
wsdl="Callback.wsdl"
packageName="examples.webservices.callback.callbackservice"/>
</jwsc>
<zip destfile="${ear-dir}/jws.war" update="true">
<zipfileset dir="src/examples/webservices/callback" prefix="wsdls">
<include name="Callback*.wsdl"/>
</zipfileset>
</zip>
</target>

jwsc Antタスクの完全なクラス名を定義するには、taskdef Antタスクを使用します。クライアントWebサービスをコンパイルするjwsc Antタスクを次のように更新します。

- デプロイ済CallbackService WebサービスのServiceインタフェース・スタブを生成およびコンパイルするため、<jws>要素の<clientgen>子要素を追加します。jwsc Antタスクでは、これらのスタブが生成されたWARファイルに自動的にパッケージ化されるため、即座にクライアントWebサービスからアクセスできるようになります。このようにするのは、生成されたクラスの1つをTartgetImpl JWSファイルでインポートして使用するためです。

- WARファイル内のCallbackServiceサービスのWSDLを含めるための<zip>要素を追加して、他のWebサービスがURL http://${wls.hostname}:${wls.port}/callback/wsdls/Callback.wsdlからWSDLにアクセスできるようにします。

jwscの詳細は、『Oracle WebLogic Server JAX-RPC Webサービスの開発』のjwsc WebLogic WebサービスAntタスクの実行に関する項を参照してください。

27 動的プロキシ・クライアントの開発

この章では、静的プロキシ・クライアントと動的プロキシ・クライアントの違いを明確にするとともに、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの動的プロキシ・クライアントを開発する手順について説明します

この章の内容は次のとおりです:

- 静的プロキシ・クライアントと動的プロキシ・クライアントの概要

- 動的プロキシ・クライアントの開発手順

- WSDLの場所を指定する際のその他の考慮事項

静的プロキシ・クライアントと動的プロキシ・クライアントの概要

表27-1は、静的プロキシ・クライアントと動的プロキシ・クライアントの違いを示しています。

表27-1 静的プロキシ・クライアントと動的プロキシ・クライアントの比較

プロキシ・クライアントのタイプ

説明

静的プロキシ・クライアント

開発時にWebサービス・クライアントをコンパイルしてバインドします。これにより、Webサービス・クライアント・プロキシの静的スタブが生成されます。生成される静的スタブ・クライアントのソース・コードは、特定のサービス実装に依存します。そのため、このオプションには柔軟性がほとんどありません。

静的プロキシ・クライアントの例は、次を参照してください。

- 『Oracle WebLogic Server 12.1.3 JAX-WS Webサービスの開発』のWebサービス・クライアントの呼出しに関する項

- 第7章「JAX-WS Webサービス・クライアントを開発するためのロードマップ」

動的プロキシ・クライアント

開発時には何もコンパイルしません。実行時にアプリケーションがWSDLの取得および解析を行い、動的に呼出しを構成します。動的プロキシ・クライアントを使用すると、実行時にclientgenを使用することなく、サービス・エンドポイント・インタフェース(SEI)に基づいて、Webサービス・クライアントからWebサービスを動的に呼び出すことが可能になります。このオプションは、特定のサービス実装に依存しないため柔軟性は増しますが、パフォーマンス・ヒットも大きくなります。

動的プロキシ・クライアントの開発手順は、「動的プロキシ・クライアントの開発手順」を参照してください。

動的プロキシ・クライアントの開発手順

動的プロキシ・クライアントを作成する手順を次の表に示します。詳細は、Javadocの「javax.xml.ws.Service」(http://docs.oracle.com/javaee/6/api/javax/xml/ws/Service.html)を参照してください。

表27-2 動的プロキシ・クライアントの作成手順

#

手順

説明

1

javax.xml.ws.Serviceインスタンスの作成

Service.createメソッドを使用してServiceインスタンスを作成します。

サービス名と、必要に応じてWSDLドキュメントの格納場所を渡す必要があります。メソッドの詳細は次のとおりです。

public static Service create (QName serviceName) throws javax.xml.ws.WebServiceException {}
public static Service create (URL wsdlDocumentLocation, QName serviceName) throws javax.xml.ws.WebServiceException {}

例:

URL wsdlLocation = new URL("http://example.org/my.wsdl");
QName serviceName = new QName("http://example.org/sample", "MyService");
Service s = Service.create(wsdlLocation, serviceName);

使用方法に関するその他の情報は、「WSDLの場所を指定する際のその他の考慮事項」を参照してください。

2

プロキシ・スタブを作成します。

Service.getPortメソッドを使用してプロキシ・スタブを作成します。このスタブを使用すると、ターゲット・サービス・エンドポイント上の操作を呼び出すことができます。

サービス・エンドポイント・インタフェース(SEI)と、必要に応じてWSDLサービス記述内のポートの名前を渡す必要があります。メソッドの詳細は次のとおりです。

public <T> T getPort(QName portName, Class<T> serviceEndpointInterface) throws javax.xml.ws.WebServiceException {}
public <T> T getPort(Class<T> serviceEndpointInterface) throws javax.xml.ws.WebServiceException {}

例:

MyPort port = s.getPort(MyPort.class);

WSDLの場所を指定する際のその他の考慮事項

HTTPSを使用してWSDLからWebサービスを取得する際に、WebLogic Server SSL証明書のホスト名定義がピアHTTPSサーバーのホスト名と同一ではない場合、または次のいずれかではない場合には、ホスト名検証エラーが発生して処理が失敗します。

- localhost

- 127.0.0.1

- localhostのホスト名

- localhostのIPアドレス

ホスト名検証エラーは次のとおりです。

EchoService service = new EchoService(https-wsdl, webservice-qName);
:
:
javax.xml.ws.WebServiceException: javax.net.ssl.SSLKeyException:
Security:090504 Certificate chain received from host.company.com - 10.167.194.63
failed hostname verification check. Certificate contained {....} but
check expected host.company.com

推奨される回避策は、サービスを作成する際にHTTPSではなくHTTPを使用してWSDLからWebサービスを取得すること、そしてサービスの作成後に独自のホスト名検証コードを使用してホスト名を検証することです。

EchoService service = Service.create(http_wsdl, qname);
//get Port
EchoPort port = service.getPort(...);
//set self-defined hostname verifier
((BindingProvider) port).getRequestContext().put(
com.sun.xml.ws.developer.JAXWSProperties.HOSTNAME_VERIFIER,
new  MyHostNameVerifier());
/*
*/

必要に応じて、バインディング・プロバイダ・プロパティを設定してホスト名検証を無視することもできます。

((BindingProvider) port).getRequestContext().put(
BindingProviderProperties.HOSTNAME_VERIFICATION_PROPERTY,
"true");

ただし、HTTPSを使用してWSDLからWebサービスを取得する必要がある場合は、いくつかの回避策が考えられます。

- WebLogic Server HTTPS接続を使用している場合は、ホスト名検証を無効にします。これを行うには、ホスト名検証を無視するグローバル・システム・プロパティを設定します。

weblogic.security.SSL.ignoreHostnameVerification=true

接続がJDK接続またはその他の非WebLogic Server接続の場合、このシステム・プロパティはサービスの作成には使用できません。

- WSDLからWebサービスを取得する前に接続に対する独自のホスト名検証を設定し、その後HTTPSを使用してWSDLからWebサービスを取得します。

//set self-defined hostname verifier
URL url = new URL(https_wsdl);
HttpsURLConnection connection = (HttpsURLConnection)url.openConnection();
connection.setHostnameVerifier(new MyHostNameVerifier());

//then initiate the service
EchoService service = Service.create(https_wsdl, qname);

//get port and set self-defined hostname verifier to binding provider
...

回避策として独自のホスト名検証を設定する場合のホスト名検証の例を次に示します。

public class MyHostnameVerifier implements HostnameVerifier {
public boolean verify(String hostname, SSLSession session) {
if (hostname.equals("the host you want"))
return true;
else
return false;
}
}

28 Webサービスのエンドポイントのパブリッシュ

この章では、javax.xml.ws.Endpoint APIを使用して、WebサービスをWebLogic Server 12.1.3インスタンスにデプロイすることなく、実行時にWebサービスのエンドポイントを作成する方法について説明します。

詳細は、 http://docs.oracle.com/javaee/6/api/javax/xml/ws/Endpoint.htmlを参照してください。

次の表に、Webサービスのエンドポイントをパブリッシュする手順をまとめます。

表28-1 Webサービスのエンド・ポイントをパブリッシュする手順

#

手順

説明

1

Webサービスのエンドポイントを作成します。

javax.xml.ws.Endpoint create()メソッドを使用してエンドポイントを作成し、エンドポイントに関連付けるインプリメンタ(Webサービスの実装)を指定し、必要に応じてバインディング・タイプを指定します。指定しない場合、バインディング・タイプのデフォルトはSOAP1.1/HTTPになります。実行時に定義したように、エンドポイントに関連付けるのは1つの実装オブジェクトと1つのjavax.xml.ws.Bindingにのみであり、これらの値は変更できません。

たとえば次の例では、CallbackWS()実装のWebサービス・エンドポイントが作成されます。

Endpoint callbackImpl = Endpoint.create(new CallbackWS());

2

受信したリクエストを受け入れるため、Webサービスのエンドポイントをパブリッシュします。

javax.xml.ws.Endpoint publish()メソッドを使用して、サーバー・コンテキストを指定するか、Webサービス・エンドポイントのアドレスとインプリメンタ(必要に応じて)を指定します。

注意: エンドポイントに関連付けられているメタデータ・ドキュメント(WSDLまたはXMLスキーマ)を更新したい場合は、エンドポイントをパブリッシュする前に更新する必要があります。

たとえば次の例では、ステップ1でサーバー・コンテキストを使用して作成したWebサービス・エンドポイントがパブリッシュされます。

Object sc
context.getMessageContext().get(MessageContext.SERVLET_CONTEXT);
callbackImpl.publish(sc);

3

Webサービスのエンドポイントを停止して、処理完了後に追加のリクエストが受け入れられないようにします。

javax.xml.ws.Endpointのstop()メソッドを使用してエンドポイントを停止し、受信したリクエストの受け入れを停止します。いったん停止したエンドポイントをパブリッシュし直すことはできません。

例:

callbackImpl.stop()

コールバック・サンプルのコンテキスト内でWebサービスのエンドポイントをパブリッシュする例については、「コールバック・クライアントWebサービスのプログラミングのガイドライン」を参照してください。

上の表に示した手順に加え、javax.xml.ws.Endpoint APIのメソッドを使用して以下を定義することもできます。

- エンドポイントに関連付けるエンドポイント・メタデータ・ドキュメント(WSDLまたはXMLスキーマ)。メタデータは、Webサービス・エンドポイントをパブリッシュする前に定義する必要があります。

- エンドポイント・プロパティ。

- アプリケーションに対する受信リクエストのディスパッチに使用するjava.util.concurrent.Executor (http://docs.oracle.com/javase/1.5.0/docs/api/java/util/concurrent/Executor.htmlを参照)。

詳細は、javax.xml.ws.EndpointのJavadoc(http://docs.oracle.com/javaee/6/api/javax/xml/ws/Endpoint.html)を参照してください。

29 XMLカタログの使用

この章では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic WebサービスでXMLカタログを使用する方法について説明します。

この章の内容は次のとおりです:

- XMLカタログの概要

- XMLカタログの定義と参照

- クライアント・ランタイムでのXMLカタログの無効化

- XMLリソースのローカル・コピーの取得

XMLカタログの概要

アプリケーションでXMLカタログを使用すると、WSDLやXSDなどのインポート済XMLリソースを、Webサービスの記述の一部ではないソースから参照できます。この方法によるXMLリソースのリダイレクトは、パフォーマンスを向上させるため、またはローカル環境においてアプリケーションを常に正しく実行できるようにするために必要になる場合があります。

たとえば、クライアントの生成時にはWSDLにアクセスできても、クライアントの実行時にはWSDLにアクセスできなくなることがあります。ネットワーク経由で参照できるリソースではなく、ローカルのリソースやアプリケーションにバンドルされているリソースを参照する必要が生じることもあります。XMLカタログ・ファイルを使用すると、Webサービスが実行時に使用するWSDLの場所を指定できます。

次の表に、WebLogic Server AntタスクでXMLカタログがどのようにサポートされるかをまとめます。

表29-1 WebLogic Server AntタスクでのXMLカタログのサポート

Antタスク

説明

clientgen

XMLカタログは、以下のいずれかの方法で定義および参照できます。

- catalog属性を使用して、外部XMLカタログ・ファイルの名前を指定します。詳細については、「外部XMLカタログの定義」を参照してください。

- <xmlcatalog>子要素を使用して埋め込んだXMLカタログ・ファイルを参照します。詳細については、「XMLカタログを埋め込み」を参照してください。

クライアントをビルドするためにclientgen Antタスク(clientgenタスクが埋み込まれている場合はjwsc Antタスク)を実行すると、jax-ws-catalog.xmlファイルが生成されてクライアントの実行時環境にコピーされます。jax-ws-catalog.xmlファイルには、外部XMLカタログ・ファイルに定義されているXMLカタログや、build.xmlファイルに埋み込まれているXMLカタログが格納されています。このファイルは、参照されるXMLターゲットとともに、エンタープライズ・アプリケーションのMETA-INFフォルダ、またはWebアプリケーションのWEB-INFフォルダにコピーされます。

注意: XMLリソースの内容は、このプロセスの間は影響を受けません。

jax-ws-catalog.xmlファイルが、クライアントの実行時環境にコピーされないようにすることもできます。詳細については、「クライアント・ランタイムでのXMLカタログの無効化」を参照してください。

wsdlc

XMLカタログは、以下のいずれかの方法で定義および参照できます。

- catalog属性を使用して、外部XMLカタログ・ファイルの名前を指定します。詳細については、「外部XMLカタログの定義」を参照してください。

- <xmlcatalog>子要素を使用して埋め込んだXMLカタログ・ファイルを参照します。詳細については、「XMLカタログを埋め込み」を参照してください。

wsdlc Antタスクを実行すると、コンパイル済みのWSDL JARファイルまたは展開されたディレクトリにXMLリソースがコピーされます。

wsdlget

XMLカタログは、以下のいずれかの方法で定義および参照できます。

- catalog属性を使用して、外部XMLカタログ・ファイルの名前を指定します。詳細については、「外部XMLカタログの定義」を参照してください。

- <xmlcatalog>子要素を使用して埋め込んだXMLカタログ・ファイルを参照します。詳細については、「XMLカタログを埋め込み」を参照してください。

wsdlget Antタスクを実行すると、WSDLとインポートされたリソースが指定のディレクトリにダウンロードされます。

注意: XMLリソースの内容は、XMLカタログに定義されているリソースの参照のため更新されます。

以降の節では、以下の内容について説明します。

- リダイレクトしたいXMLリソースを指定するため、XMLカタログを定義して参照する方法。「XMLカタログの定義と参照」を参照してください。

- クライアント・ランタイムでXMLカタログを無効化する方法。「クライアント・ランタイムでのXMLカタログの無効化」を参照してください。

- wsdlgetを使用して、WSDLとそのインポート済みXMLリソースのローカル・コピーを取得する方法。これらのファイルは、アプリケーションにパッケージ化し、XMLカタログ内から参照できます。「XMLリソースのローカル・コピーの取得」を参照してください。

XMLカタログの詳細は、(http://www.oasis-open.org/committees/download.php/14809/xml-catalogs.html)のOasis XMLカタログ仕様を参照してください。

XMLカタログの定義と参照

XMLカタログは、以下のいずれかの方法で作成し、build.xmlファイル内のclientgenまたはwsdlc Antタスクから参照できます。

- 外部XMLカタログの定義 - 外部XMLカタログ・ファイルを定義し、そのファイルをbuild.xmlファイル内のclientgenまたはwsdlc Antタスクからcatalogs属性を使用して参照します。詳細については、「外部XMLカタログの定義」を参照してください。

- XMLカタログの埋め込み - <xmlcatalog>要素を使用してXMLカタログを直接build.xmlファイルに埋め込み、<xmlcatalog>子要素を使用してbuild.xmlファイル内のclientgenまたはwsdlc Antタスクから参照します。詳細については、「XMLカタログを埋め込み」を参照してください。

競合が発生した場合は、外部XMLカタログに定義されているエントリよりも、埋め込みXMLカタログに定義されているエントリが優先されます。

注意:
wsdlget Antタスクを使用すると、XMLリソースのローカル・コピーを取得できます。詳細については、「クライアント・ランタイムでのXMLカタログの無効化」を参照してください。

外部XMLカタログの定義

外部XMLカタログを定義するには:

1. リダイレクトしたいXMLリソースを定義した外部XMLカタログを作成します。「外部XMLカタログ・ファイルの作成」を参照してください。

2. 作成したXMLカタログ・ファイルを、catalogs属性を使用してbuild.xmlファイル内のclientgenまたはwsdlc Antタスクから参照します。「外部XMLカタログ・ファイルの参照」を参照してください。

以降の節では、これらの各手順について詳しく説明します。

外部XMLカタログ・ファイルの作成

<catalog>要素はXMLカタログのルート要素で、XMLカタログ・エントリのコンテナとして機能します。XMLカタログ・エンティティを指定するには、たとえばsystem要素やpublic要素を使用します。

次に、XMLカタログ・ファイルのサンプルを示します。

<catalog xmln="urn:oasis:names:tc:entity:xmlns:xml:catalog"
prefer="system">
<system systemId="http://foo.org/hello?wsdl"
uri="HelloService.wsdl" />
<public publicId="ISO 8879:1986//ENTITIES Added Latin 1//EN"
uri="wsdl/myApp/myApp.wsdl"/>
</catalog>

このサンプルで注目すべき点は以下のとおりです。

- <catalog>ルート要素によってXMLカタログのネームスペースが定義され、システムの一致が優先されることを指定するためprefer属性がsystemに設定されています。

- <system>要素により、URI参照がシステムIDに関連付けられています。

- <public>要素により、URI参照がパブリックIDに関連付けられています。

XMLカタログ・ファイル構文の詳細は、(http://www.oasis-open.org/committees/download.php/14809/xml-catalogs.html)のOasis XMLカタログ仕様を参照してください。

外部XMLカタログ・ファイルの参照

作成したXMLカタログ・ファイルをbuild.xmlファイル内のclientgenまたはwsdlc Antタスクから参照するには、catalogs属性を使用します。

次のサンプルでは、clientgenを使用してXMLカタログを参照する方法を示します。関連するコード行は太字で示されています。

<target name="clientgen">
<clientgen
type="JAXWS"
wsdl="${wsdl}"
destDir="${clientclasses.dir}"
packageName="xmlcatalog.jaxws.clientgen.client"
catalog="wsdlcatalog.xml"/>
</clientgen>
</target>

XMLカタログを埋め込み

XMLカタログを埋め込むには:

1. build.xmlファイル内に埋め込みXMLカタログを作成します。「埋め込みXMLカタログの作成」を参照してください。

2. 作成した埋め込みXMLカタログを、xmlcatalog子要素を使用してclientgenまたはwsdlc Antタスクから参照します。「埋め込みXMLカタログの参照」を参照してください。

以降の節では、これらの各手順について詳しく説明します。

注意:
競合が発生した場合は、外部XMLカタログに定義されているエントリよりも、埋め込みXMLカタログに定義されているエントリが優先されます。

埋め込みXMLカタログの作成

<xmlcatalog>要素を使用すると、XMLカタログを直接build.xmlファイルに埋め込むことができます。次のサンプルに、build.xmlファイルに埋め込まれたXMLカタログを示します。

<xmlcatalog id="wsimportcatalog">
<entity publicid="http://helloservice.org/types/HelloTypes.xsd"
location="${basedir}/HelloTypes.xsd"/>
</xmlcatalog>

XMLカタログ・ファイル構文の詳細は、(http://www.oasis-open.org/committees/download.php/14809/xml-catalogs.html)のOasis XMLカタログ仕様を参照してください。

埋め込みXMLカタログの参照

clientgenまたはwsdlc Antタスクの<xmlcatalog>子要素を使用すると、埋め込みXMLカタログを参照できます。<xmlcatalog>要素を指定するには、次の構文を使用します:

<xmlcatalog refid="id"/>

<Xmlcatalog>子要素によって参照されるidは、埋め込みXMLカタログのIDと一致している必要があります。

次のサンプルでは、clientgenを使用して埋め込みXMLカタログを参照する方法を示します。関連するコード行は太字で示されています。

<target name="clientgen">
<clientgen
type="JAXWS"
wsdl="${wsdl}"
destDir="${clientclasses.dir}"
packageName="xmlcatalog.jaxws.clientgen.client"
catalog="wsdlcatalog.xml"/>
<xmlcatalog refid="wsimportcatalog"/>
</clientgen>
</target>
<xmlcatalog id="wsimportcatalog">
<entity publicid="http://helloservice.org/types/HelloTypes.xsd"
location="${basedir}/HelloTypes.xsd"/>
</xmlcatalog>

クライアント・ランタイムでのXMLカタログの無効化

「XMLカタログの定義と参照」に従ってbuild.xmlファイル内でXMLカタログを定義して参照する場合、clientgen Antタスクを実行してクライアントをビルドすると、デフォルトではjax-ws-catalog.xmlファイルが生成されてクライアント実行時環境にコピーされます。jax-ws-catalog.xmlファイルには、外部XMLカタログ・ファイルに定義されているXMLカタログや、build.xmlファイルに埋み込まれているXMLカタログが格納されています。このファイルは、参照されるXMLターゲットとともに、エンタープライズ・アプリケーションのMETA-INFフォルダ、またはWebアプリケーションのWEB-INFフォルダにコピーされます。

クライアント実行時環境でのXMLカタログ・アーティファクトの生成は、clientgenのgenRuntimeCatalog属性をfalseに設定することで無効にできます。例:

<clientgen
type="JAXWS"
wsdl="${wsdl}"
destDir="${clientclasses.dir}"
packageName="xmlcatalog.jaxws.clientgen.client"
catalog="wsdlcatalog.xml"
genRuntimeCatalog="false"/>

この場合、jax-ws-catalog.xmlファイルは実行時環境にはコピーされません。

genRuntimeCatalog属性をfalseに設定した状態でクライアントを生成した場合、後からクライアント・ランタイムでXMLカタログを有効にするには、jax-ws-catalog.xmlファイルを手動で作成し、エンタープライズ・アプリケーションのMETA-INFフォルダまたはWebアプリケーションのWEB-INFフォルダにコピーする必要があります。jax-ws-catalog.xmlファイルには、外部XMLカタログ・ファイルに定義されているすべてのエントリ、またはbuild.xmlファイルに埋め込まれているすべてのエントリが含まれていることを確認します。

XMLリソースのローカル・コピーの取得

wsdlget Antタスクを使用すると、WSDLやXSDファイルなどのXMLリソースのローカル・コピーを取得できます。その後は、「XMLカタログの定義と参照」で説明したとおり、XMLカタログを使用してXMLリソースのローカル・コピーを参照できます。

次に示すAnt build.xmlファイルの抜粋に、wsdlget Antタスクを使用してWSDLとそのXMLリソースをダウンロードする方法を示します。XMLリソースは、Antタスクの実行ディレクトリ内のwsdlフォルダに保存されます。

<target name="wsdlget"
<wsdlget
wsdl="http://host/service?wsdl"
destDir="./wsdl/"
/>
</target>

30 XML over HTTPを使用するWebサービスのプログラミング

この章では、XML over HTTPを使用するWebLogic Server 12.1.3用のWebサービスのプログラミング方法について説明します。

この章の内容は次のとおりです:

- XML over HTTPを使用するWebサービスのプログラミングの概要

- XML over HTTPを使用するWebサービスのプログラミングのガイドライン

- クライアントからWebサービスにアクセスする

- XML over HTTPを使用するWebサービスの保護

XML over HTTPを使用するWebサービスのプログラミングの概要

標準的なSOAP over HTTPの使用例に加えて、XML over HTTP方式の一部のWebサービスでもWebLogic JAX-WSを使用できます。XML over HTTP方式を使用すると、JAX-WSプログラミング・モデルの利便性を活用しながら、単純でRESTfulなWebサービスを構築できます。

注意:
ベスト・プラクティスとしてお薦めする方法は、Jersey JAX-RS RIを使用してRESTfulなWebサービスを開発することです(『Oracle WebLogic Server RESTful Webサービスの開発と保護』を参照)。Jersey JAX-RS RIでは、RESTfulなWebサービスを構築するために本番環境として使用できるオープン・ソースのRIが提供され、すべてのHTTPメソッドがサポートされます。

HTTPプロトコルを使用してWebサービス・リソースにアクセスする場合、リソース識別子はリソースのURLであり、このリソースで実行される標準の操作はHTTPの1つのメソッド(GET、PUT、DELETE、POST、またはHEAD)です。

注意:
このJAX-WS実行で、サポートされたHTTPメソッドのセットがGETおよびPOSTに限定されています。DELETE、PUTおよびHEADがサポートされません。これらのメソッドを含むどのHTTPリクエストも405不可のメソッドというエラー・メッセージが表示され、拒否されます。
PUTおよびDELETEの機能が必須の場合、POSTメソッドで実行される実際のメソッドをトンネリングすることによって目的のアクションを実行できます。これは、オーバーロードPOSTと呼ばれる回避策です。(「REST過負荷POST」でのWeb検索は、これを実行するためのいくつかの方法を返します。)

javax.xml.ws.Provider<T>インタフェースのinvoke()メソッドを使用してRESTfulに類似したエンドポイントを構築します(http://docs.oracle.com/javaee/6/api/javax/xml/ws/Provider.htmlを参照)。Providerインタフェースは、サービス・エンドポイント・インタフェース(SEI)を構築するための動的な代替手段を提供します。

この項の手順では、XML over HTTPを使用してWebサービスを実装するために必要なJWSファイルをプログラミングおよびコンパイルする方法について説明します。この手順では、これらのJWSファイルをゼロから作成する方法を示しています。既存のJWSファイルを更新する場合は、この手順をガイドとして利用してください。

Antベースの開発環境を設定済であり、かつjwsc Antタスクを実行してWebサービスをデプロイするためのターゲットを追加できる、作業用のbuild.xmlファイルがあることが前提となっています。詳細は、第3章「JAX-WS Webサービスの開発」を参照してください。

表30-1 RESTfulなWebサービスのプログラミング手順

#

手順

説明

1

XML over HTTPを使用するWebサービスを実装する、新しいJWSファイルを作成するか、既存のJWSファイルを更新します。

使い慣れたIDEまたはテキスト・エディタを使用します。「XML over HTTPを使用するWebサービスのプログラミングのガイドライン」を参照してください。

2

build.xmlファイルを更新して、JWSファイルをWebサービスにコンパイルするjwsc Antタスクの呼出しを含めます。

例:

<jwsc srcdir="." destdir="output/restEar">
<jws file="NearbyCity.java" type="JAXWS"/>
</jwsc>

詳細は、「jwsc WebLogic WebサービスAntタスクの実行」を参照してください。

3

Antターゲットを実行して、Webサービスを構築します。

例:

prompt> ant build-rest

4

Webサービスを通常どおりデプロイします。

「WebLogic Webサービスのデプロイとアンデプロイ」を参照してください。

5

Webサービス・クライアントからWebサービスにアクセスします。

「クライアントからWebサービスにアクセスする」を参照してください。

XML over HTTPを使用するWebサービスのプログラミングのガイドライン

次のサンプルでは、XML over HTTPを使用するWebサービスを実装する簡単なJWSファイルを示します。太字で示されたJavaコードに対応するコーディングのガイドラインについては、サンプルの後の説明を参照してください。

package examples.webservices.jaxws.rest;
import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.BindingType;
import javax.xml.ws.Provider;
import javax.xml.ws.WebServiceContext;
import javax.xml.ws.handler.MessageContext;
import javax.xml.ws.http.HTTPBinding;
import javax.xml.ws.http.HTTPException;
import javax.xml.transform.Source;
import javax.xml.transform.stream.StreamSource;
import javax.annotation.Resource;
import java.io.ByteArrayInputStream;
import java.util.StringTokenizer;

@WebServiceProvider(
targetNamespace="http://example.org",
serviceName = "NearbyCityService")
@BindingType(value = HTTPBinding.HTTP_BINDING)

public class NearbyCity implements Provider<Source> {
@Resource(type=Object.class)
protected WebServiceContext wsContext;

public Source invoke(Source source)  {
try {
MessageContext messageContext = wsContext.getMessageContext();

// Obtain the HTTP mehtod of the input request.
javax.servlet.http.HttpServletRequest servletRequest =
(javax.servlet.http.HttpServletRequest)messageContext.get(
MessageContext.SERVLET_REQUEST);
String httpMethod = servletRequest.getMethod();
if (httpMethod.equalsIgnoreCase("GET"));
{

String query =
(String)messageContext.get(MessageContext.QUERY_STRING);
if (query != null && query.contains("lat=") &&
query.contains("long=")) {
return createSource(query);
} else {
System.err.println("Query String = "+query);
throw new HTTPException(404);
}
} catch(Exception e) {
e.printStackTrace();
throw new HTTPException(500);
}
}
} else {
// This operation only supports "GET"
throw new HTTPException405);
}
private Source createSource(String str) throws Exception {
StringTokenizer st = new StringTokenizer(str, "=&/");
String latLong = st.nextToken();
double latitude = Double.parseDouble(st.nextToken());
latLong = st.nextToken();
double longitude = Double.parseDouble(st.nextToken());
City nearby = City.findNearBy(latitude, longitude);
String body = nearby.toXML();
return new StreamSource(new ByteArrayInputStream(body.getBytes()));
}

static class City {
String city;
String state;
double latitude;
double longitude;
City(String city, double lati, double longi, String st) {
this.city = city;
this.state = st;
this.latitude = lati;
this.longitude = longi;
}

double distance(double lati, double longi) {
return Math.sqrt((lati-this.latitude)*(lati-this.latitude) +
(longi-this.longitude)*(longi-this.longitude)) ;
}

static final City[] cities = {
new City("San Francisco",37.7749295,-122.4194155,"CA"),
new City("Columbus",39.9611755,-82.9987942,"OH"),
new City("Indianapolis",39.7683765,-86.1580423,"IN"),
new City("Jacksonville",30.3321838,-81.655651,"FL"),
new City("San Jose",37.3393857,-121.8949555,"CA"),
new City("Detroit",42.331427,-83.0457538,"MI"),
new City("Dallas",32.7830556,-96.8066667,"TX"),
new City("San Diego",32.7153292,-117.1572551,"CA"),
new City("San Antonio",29.4241219,-98.4936282,"TX"),
new City("Phoenix",33.4483771,-112.0740373,"AZ"),
new City("Philadelphia",39.952335,-75.163789,"PA"),
new City("Houston",29.7632836,-95.3632715,"TX"),
new City("Chicago",41.850033,-87.6500523,"IL"),
new City("Los Angeles",34.0522342,-118.2436849,"CA"),
new City("New York",40.7142691,-74.0059729,"NY")};
static City findNearBy(double lati, double longi) {
int n = 0;
for (int i = 1; i < cities.length; i++)  {
if (cities[i].distance(lati, longi) <
cities[n].distance(lati, longi)) {
n = i;
}
}
return cities[n];
}

public String toXML() {
return "<ns:NearbyCity xmlns:ns=\"http://example.org\"><City>"
+this.city+"</City><State>"+ this.state+"</State><Lat>"
+this.latitude +
"</Lat><Lng>"+this.longitude+"</Lng></ns:NearbyCity>";
}
}
}

XML over HTTPを使用するWebサービスを実装するJWSファイルをプログラミングする際には、次のガイドラインに従います。ガイドラインのコード・スニペットは、前述のサンプルでは太字で示されています。

- プロバイダWebサービスを実装するために必要なパッケージをインポートします。

import javax.xml.ws.WebServiceProvider;
import javax.xml.ws.BindingType;
import javax.xml.ws.Provider;

- Provider実装クラスにアノテーションを追加し、HTTPに対するバインディング・タイプを設定します。

@WebServiceProvider(
targetNamespace="http://example.org",
serviceName = "NearbyCityService")
@BindingType(value = HTTPBinding.HTTP_BINDING)

- Providerインタフェースのinvoke()メソッドを実装します。

public class NearbyCity implements Provider<Source> {
@Resource(type=Object.class)
protected WebServiceContext wsContext;

public Source invoke(Source source)  {
...
}

- 処理するために、javax.xml.ws.handler.MessageContextでQUERY_STRINGフィールドを使用してリクエスト文字列を取得します(メッセージURL http://docs.oracle.com/javaee/6/api/javax/xml/ws/handler/MessageContext.htmlを参照)。その後、問合せ文字列がcreateSource()メソッドに渡され、指定した値に最も近い市、州、緯度、経度が返されます。

String query =
(String)messageContext.get(MessageContext.QUERY_STRING);
.
.
.
return createSource(query);

クライアントからWebサービスにアクセスする

Webサービス・クライアントからWebサービスにアクセスするには、リソースのURIを使用します。例:

URL url = new URL (http://localhost:7001/NearbyCity/NearbyCityService?lat=35&long=-120);
HttpURLConnection conn = (HttpURLConnection)url.openConnection();
connection.setRequestMethod("POST");
// Get result
InputStream is = connection.getInputStream();

この例では、緯度(lat)と経度(long)の値を指定して、必要なリソースにアクセスしています。

XML over HTTPを使用するWebサービスの保護

Webアプリケーションの保護に使用するメソッドと同じメソッドを使用して、XML over HTTPを使用するWebサービスを保護することができます。詳細は、『Oracle WebLogic Serverロールおよびポリシーによるリソースの保護』のWebアプリケーションおよびEJBリソースの保護のオプションに関する項を参照してください。

31 HTTPセッションを使用したステートフルJAX-WS Webサービスのプログラミング

この章では、Oracleデータベースと対話する、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスの開発方法について説明します。

この章の内容は次のとおりです:

- ステートフルWebサービスの概要

- サーバーでHTTPセッションにアクセスする

- クライアントでのHTTPセッションの有効化

- セッション状態レプリケーションを使用してクラスタ内のステートフル・サービスを開発する

- JAX-WS RI @ステートフル拡張に関する注意

ステートフルWebサービスの概要

通常、JAX-WS Webサービスはステートレスです。つまり、Webサービス・オブジェクトに設定したどのローカル変数とオブジェクト値も、1つの呼出しから次の呼び出しまで保存されません。1つのクライアントからの順次的な各リクエストも独立、ステートレス・メソッド呼出しとして扱われます。

Webサービスの使用例として、クライアントが呼出しの途中でサービスにデータを保存しておき、その後の呼出しで保存したデータを使用するというものがあります。たとえば、ショッピング・カート・オブジェクトを、addToCart Webメソッドを繰り返し呼び出して追加した後、getCart webメソッドで取得するとします。ステートレスWebサービスでは、addToCartメソッド呼出しの数に関係なく、ショッピング・カート・オブジェクトは常に空となります。しかし、HTTPセッションを使用して複数のWebサービス呼出しにわたって状態を保持すれば、カートの中身を徐々に増やした後、カートをクライアントに戻すことができます。

JAX-WS Webサービスでのステートフル・サポートは、クライアント側、サーバー側ともに最小限のコーディングで有効にできます。

サーバーでHTTPセッションにアクセスする

サーバーでは、すべてのWebサービス呼出しがHttpSessionオブジェクトに関連付けられています。このオブジェクトは、リソース・インジェクションを使用してWebサービス・オブジェクトにバインドされているWebサービス・コンテキストからアクセス可能です。HttpSessionオブジェクトにアクセスしたら、それに任意のステートフル・オブジェクトを「ハング」オフできます。クライアントが次にWebサービスを呼び出すと、Webサービスは同じHttpSessionオブジェクトを見つけて、その中に以前格納したオブジェクトを参照することができます。これでWebサービスはステートフルになりました。

サーバーでの必要な手順は以下のとおりです。

1. Webサービスの冒頭に(Common Annotations for the Java Platform、JSR 250で定義されている)@Resourceを追加します。

2. コンテキストが注入されているWebServiceContext型の変数を追加します。

3. Webサービス・コンテキストを使用してHttpSessionオブジェクトを取得します。

4. setAttributeメソッドを使用してHttpSessionにオブジェクトを保存し、getAttributeを使用して格納されたオブジェクトを取得します。オブジェクトが割り当てる文字列値によって識別されます。

次のスニペットは、その使い方を示します:

例31-1 サーバーでのHTTPセッションへのアクセス

@WebService
public class ShoppingCart {
@Resource    // Step 1
private WebServiceContext wsContext;    // Step 2
public int addToCart(Item item) {
// Find the HttpSession
MessageContext mc = wsContext.getMessageContext();    // Step 3
HttpSession session = ((javax.servlet.http.HttpServletRequest)mc.get(MessageContext.SERVLET_REQUEST)).getSession();
if (session == null)
throw new WebServiceException("No HTTP Session found");
// Get the cart object from the HttpSession (or create a new one)
List<Item> cart = (List<Item>)session.getAttribute("myCart");  // Step 4
if (cart == null)
cart = new ArrayList<Item>();
// Add the item to the cart (note that Item is a class defined
// in the WSDL)
cart.add(item);
// Save the updated cart in the HTTPSession (since we use the same
// "myCart" name, the old cart object will be replaced)
session.setAttribute("myCart", cart);
// return the number of items in the stateful cart
return cart.size();
}
}

クライアントでのHTTPセッションの有効化

クライアント側コードはとても簡単です。必要なのは、リクエスト・コンテキストにSESSION_MAINTAIN_PROPERTYを設定することのみです。これにより、Webサービスから受信したHTTP Cookieを戻すようクライアントに指示します。Cookieには、サーバーがWebサービス呼出しを正しいHttpSessionと対応させるためのセッションIDが含まれており、これによって任意の保存済ステートフル・オブジェクトへのアクセスが可能になります。

例31-2 クライアントのHTTPセッションの有効化

ShoppingCart proxy = new CartService().getCartPort();
((BindingProvider)proxy).getRequestContext().put(BindingProvider.SESSION_MAINTAIN_PROPERTY, true);
// Create a new Item object with a part number of '123456' and an item
// count of 4.
Item item = new Item('123456', 4);
// After first call, we'll print '1' (the return value is the number of objects
// in the Cart object)
System.out.println(proxy.addToCart(item));
// After the second call, we'll print '2', since we've added another
// Item to the stateful, saved Cart object.
System.out.println(proxy.addToCart(item));

セッション状態レプリケーションを使用してクラスタ内のステートフル・サービスを開発する

高可用性環境では、1つのJAX-WS Webサービスがクラスタ内の複数のサーバー・インスタンスにレプリケートされる場合があります。このような環境でステートフルJAX-WS Webサービスをサポートするには、WebLogic Server HTTPセッション状態レプリケーション機能を使用します。詳細は、『Oracle WebLogic Serverクラスタの管理』のHTTPセッション状態レプリケーションに関する項を参照してください。

セッション状態レプリケーションを使用してクラスタ化された環境を設定するには、様々な技術要件および構成要件(サポートされているサーバーやロード・バランサなど)があります。JAX-WSプログラミングの観点から、唯一の新しい考慮事項は、(例31-1に示されているように)HttpSession.setAttributeメソッドを使用してHttpSessionに格納するオブジェクトはシリアライズ可能であることが必要な点です。シリアライズ可能であると、クラスタ内のレプリケートされたすべてのWebインスタンス上のWebサービスに対してそれらのステートフル・オブジェクトが使用可能になり、JAX-WSステートフルWebサービスでロード・バランシングとフェイルオーバーの両方の機能を使用できるようになります。

JAX-WS RI @ステートフル拡張に関する注意

JAX-WS 2.1 Reference Implementation (RI)には、@Statefulアノテーションを使用してステートフルJAX-WS Webサービスの異なるモデルをサポートするベンダー拡張があります。その実装は、状態を特定のインスタンスに固定するもので、スケーラビリティやフォルト・トレランスを目的としていません。WebLogic Server JAX-WS Webサービスでは、この機能はサポートされません。

32 Webサービスのテストおよび監視

この章では、WebLogic Server 12.1.3のWebLogic Webサービスの開発および管理に使用できるツールについて説明します。

この章の内容は次のとおりです。

- Webサービスのテスト

- Webサービスおよびクライアントの監視

- ワーク・マネージャによるWebサービス作業の優先付けとスタック実行スレッドの削減

Webサービスのテスト

セキュリティ、サービス品質(QoS)、HTTPヘッダーなど、Webサービスの基本機能および高度な機能をテストできます。セキュリティ機能のストレス・テストを実行することもできます。Webサービス・テスト・クライアントまたはFusion Middleware Controlの「Webサービスのテスト」ページを使用したWebサービスのテストの詳細は、『Webサービスの管理』のWebサービスのテストに関する項を参照してください。

Webサービスとクライアントのモニター

WebLogic Server管理コンソールまたはWLSTを使用して、呼出し回数、エラー数、フォルト数などのWebサービスおよびクライアントの実行時の情報を監視できます。

次の命名規則では、監視ページでWebサービスまたはクライアントを特定します。

<application_name>#<application_version>!<service_name><contextpath><url_pattern>

説明:

- application_name - Webサービスまたはクライアントを含むアプリケーションの名前。

- application_version - Webサービスまたはクライアントを含むアプリケーションのバージョン。

- service_name - Webサービスまたはクライアントの名前。

- context_path - Webサービス用に定義されるコンテキスト・パス。詳細は、「WebLogic Webサービスのコンテキスト・パスの定義」を参照してください。

- url_pattern - システム・デフォルトまたはユーザー定義によるWebサービスのURLパターン。詳細は、「Webサービスの呼出しに使用されるトランスポートの指定」を参照してください。

Webサービスの監視

WebLogic Server管理コンソールを使用してWebサービスを監視するには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表でWebサービスがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開すると、「Webサービス」カテゴリにアプリケーション内のWebサービスのリストが表示されます。Webサービスの名前をクリックし、「監視」タブをクリックします。

または、左ペインの「デプロイメント」ノード、右ペインに表示される「監視」タブ、「Webサービス」タブの順にクリックします。監視統計を表示するWebサービスの名前をクリックします。

次の表に、Webサービス情報を監視するために選択できるタブを示します。各ページでは、Webサービスが実行されているすべてのサーバーの統計が集計されます。

注意:
JAX-WS Webサービスの場合、組込みのWs-Protocol操作では、基になるWS-*プロトコルに関する統計情報が表示されます。この情報は、アプリケーションのパフォーマンスを評価するときに役立ちます。

表32-1 Webサービスの監視

クリックするタブ

表示される内容

「監視」→「全般」

合計エラー数や呼出し数など、Webサービスに関する一般的な統計。

「監視」→「呼出し」

ディスパッチ時間、実行時間および平均など、呼出しの統計。

「監視」→「WS-Policy」

Webサービスにアタッチされているポリシー。認証、認可、機密性、整合性のカテゴリに編成されています。

「監視」→「ポート」

Webサービス・エンドポイント(ポート)がリストされている表。この表には、各ポートの情報がまとめられています。ポート名をクリックすると、詳細が表示されます。

「監視」→「ポート」→「全般」

Webサービス・エンドポイントに関する一般的な統計。ページには、Webサービス・エンドポイント名、そのURI、関連付けられているWebサービス、エンタープライズ・アプリケーション、およびアプリケーション・モジュールなどの情報が表示されます。すべてのWebサービス・エンドポイント操作に関して、エラー数と呼出し数が集約されます。

「監視」→「ポート」→「呼出し」

成功、失敗、違反の数など、Webサービス・エンドポイントの呼出しの統計。

「監視」>「ポート」>「クラスタ・ルーティング」

リクエストとレスポンス、およびルーティング失敗など、Webサービス・エンドポイントのクラスタ・ルーティングの統計。

「監視」→「ポート」→「接続」

WebサービスのMakeConnection非同期エンドポイント。非同期エンドポイントごとに、受信メッセージ数、保留メッセージ数など、実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

非同期エンドポイントの名前をクリックして詳細を表示します。

「監視」→「ポート」→「信頼できるメッセージ」

Webサービスの信頼性のあるメッセージングの順序。信頼性のあるメッセージングの順序ごとに、順序の状態、移行元サーバーおよび宛先サーバーなどの実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

順序IDをクリックして詳細を表示します。

「監視」→「ポート」→「リクエスト」

Webサービスの信頼性のあるメッセージング・リクエスト。信頼性のあるメッセージング・リクエストごとに、実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

信頼できるメッセージIDをクリックして詳細を表示します。

「監視」→「ポート」→「WS-Policy」

Webサービス・エンドポイントにアタッチされているポリシーに関連した統計。認証、認可、機密性、整合性のカテゴリに編成されています。

「監視」→「ポート」→「操作」

Webサービス・エンドポイントの操作のリスト。

WebLogic Serverインスタンスが起動されてから操作が呼び出された回数、Webサービスの呼出しにかかった平均時間、レスポンスにかかった時間など、各操作に関する実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

注意: JAX-WS Webサービスの場合、組込みのWs-Protocol操作では、基になるWS-*プロトコルに関する統計情報が表示されます。たとえば、Webサービスの信頼性メッセージでは、この操作により、Webサービスまたはクライアントの代理で信頼性のあるメッセージサブシステムによって送受信されるCreateSequenceメッセージおよびAckRequestedメッセージのメッセージ統計を取得します。この情報は、アプリケーションのパフォーマンスを評価するときに役立ちます。

操作の名前をクリックすると詳細が表示されます。選択した操作の一般的な統計や呼出しの統計を表示するには、それぞれ「一般」または「呼出し」タブをクリックします。

Webサービス・クライアントの監視

WebLogic Server管理コンソールを使用してWebサービス・クライアントを監視するには、左ペインの「デプロイメント」ノードをクリックし、右ペインに表示される「デプロイメント」表でWebサービスがパッケージ化されているエンタープライズ・アプリケーションを探します。「+」ノードをクリックしてアプリケーションを展開し、Webサービス・クライアントが存在するアプリケーション・モジュールをクリックします。「監視」タブ「Webサービス・クライアント」タブの順にクリックします。

または、左ペインの「デプロイメント」ノード、右ペインに表示される「監視」タブ、「Webサービス・クライアント」タブの順にクリックします。監視統計を表示するWebサービス・クライアントの名前をクリックします。

表には、各Webサービス・クライアントの実行時の情報がまとめて表示されます。表でクライアント名をクリックすると詳細が表示されます。

注意:
JAX-WS Webサービスの場合、Webサービスの実行時、Webサービス・エンドポイント内にシステム定義のクライアント・インスタンスを作成し、それを使用してエンドポイントに定められたプロトコル固有のメッセージを送信します。これらのクライアント・インスタンスには、クライアント・インスタンスが属するWebサービス・エンドポイントの名前に基づき、接尾辞が-SystemClientの名前が付けられます。システム定義のクライアント・インスタンスに関する監視情報を利用して、アプリケーションを評価できます。

表32-2 Webサービス・クライアントの監視

クリックするタブ

表示される内容

「監視」→「全般」

エラーや呼出しの合計数など、Webサービス・クライアントに関する一般的な統計。ページには、Webサービス・クライアント名、関連付けられているエンタープライズ・アプリケーションとアプリケーション・モジュール、およびコンテキスト・ルートが表示されます。Webサービスが実行されているすべてのサーバーに関して、エラーと呼出しの統計が集約されます。

「監視」→「呼出し」

ディスパッチ時間、実行時間および平均など、呼出しの統計。

「監視」→「WS-Policy」

Webサービス・クライアントにアタッチされているポリシー。認証、認可、機密性、整合性のカテゴリに編成されています。

「監視」>「サーバー」

現在クライアントが実行されているサーバーがリストされている表。そのサーバーのWebサービス・クライアントに関する詳細を表示するには、クライアント名をクリックし、この後の手順のタブを使用します。

「監視」→「サーバー」→「全般」

Webサービス・クライアントに関する一般的な統計。ページには、Webサービス・クライアント・ポート、関連付けられているエンタープライズ・アプリケーションとアプリケーション・モジュール、およびコンテキスト・ルートなどの情報が表示されます。すべてのWebサービス・クライアント操作に関して、エラー数と呼出し数が集約されます。

「監視」→「サーバー」→「呼出し」

成功、失敗、違反の数など、Webサービス・クライアントの呼出しの統計。

「監視」>「サーバー」>「クラスタ・ルーティング」

リクエストとレスポンス、ルーティングの失敗など、Webサービス・クライアントのクラスタ・ルーティングの統計。詳細は、第23章「クラスタのルーティング・パフォーマンスのモニター」を参照してください。

「監視」→「サーバー」→「接続」

Webサービス・クライアントのMakeConnection非同期エンドポイント。非同期エンドポイントごとに、受信メッセージ数、保留メッセージ数など、実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

非同期エンドポイントの名前をクリックして詳細を表示します。

「監視」→「サーバー」→「信頼できるメッセージ」

Webサービス・クライアントの信頼性のあるメッセージングの順序。信頼性のあるメッセージングの順序ごとに、順序の状態、移行元サーバーおよび宛先サーバーなどの実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

非同期エンドポイントの名前をクリックして詳細を表示します。

「監視」→「サーバー」→「WS-Policy」

Webサービス・クライアントにアタッチされているポリシーに関連した統計。認証、認可、機密性、整合性のカテゴリに編成されています。

「監視」→「サーバー」→「操作」

Webサービス・クライアントの操作のリスト。レスポンス、実行およびディスパッチの平均時間、レスポンス、呼出しおよびエラーの数など、各操作に関する実行時の監視情報が表示されます。「この表のカスタマイズ」をクリックして、表に表示される情報をカスタマイズできます。

操作の名前をクリックすると詳細が表示されます。選択した操作の一般的な統計や呼出しの統計を表示するには、それぞれ「一般」または「呼出し」タブをクリックします。

ワーク・マネージャによるWebサービス作業の優先付けとスタック実行スレッドの削減

クライアント・アプリケーションとWebサービスの間の接続が確立されると、理論的にはこれらの間の対話がスムーズかつ迅速になり、クライアントによるリクエストとサービスによるレスポンスが適切なタイミングで行われます。ただし、クライアント・アプリケーションが新しいリクエストを行うのに時間がかかり、その間(最長でWebLogic Serverインスタンスの存続時間の間)、Webサービスが応答を待機する状況が発生することもあります。これは、しばしばスタック実行スレッドと呼ばれます。ある一時点においてスタック実行スレッドが大量に発生すると、サーバー全体のパフォーマンスが低下する可能性があります。

特定のWebサービスが頻繁にこのような状態になる場合は、ワーク・マネージャを構成してサービスに適用することで、そのサービスにおいて作業の実行をどのように優先付けするかを指定できます。たとえば、レスポンス時間リクエスト・クラス(特定のタイプのワーク・マネージャ・コンポーネント)を構成すると、Webサービスのレスポンス時間の目標値を指定できます。

次に、デプロイメント記述子でレスポンス時間リクエスト・クラスを定義する方法の例を示します。

<work-manager>
<name>responsetime_workmanager</name>
<response-time-request-class>
<name>my_response_time</name>
<goal-ms>2000</goal-ms>
</response-time-request-class>
</work-manager>

Oracle WebLogic Server管理コンソール・オンライン・ヘルプのワーク・マネージャ: レスポンス時間: 構成に関する項の説明に従って、WebLogic Server管理コンソールを使用してレスポンス時間リクエスト・クラスを構成できます。

ワーク・マネージャの詳細、およびWebサービスに対して構成する方法については、『Oracle WebLogic Serverサーバー環境の管理』のワーク・マネージャを使用したスケジューリング済作業の最適化に関する項を参照してください。

第V部

リファレンス

第V部の章の内容は次のとおりです。

- 付録A「Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル」

- 付録B「信頼性のあるメッセージングのバッチ化のためのクライアント・ラッパー・クラスの例」

- 付録C「JAX-WSへのJAX-RPC Webサービスおよびクライアントの移行」

A Webサービスの信頼性のあるメッセージングと接続作成のためのあらかじめパッケージ化されたWS-Policyファイル

この付録では、あらかじめパッケージ化されたWS-Policyファイルの概要を説明します。WS-Policyファイルは、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスで、信頼性のあるメッセージング、接続作成、またはこの両方の機能をサポートします。

これらのあらかじめパッケージ化されたファイルを変更することはできません。これらの値がニーズに合ない場合は、独自のWS-Policyファイルを作成する必要があります。詳細は、次を参照してください。

- Webサービスの信頼性のあるメッセージングのWS-Policyファイルの作成

- Webサービスの接続作成WS-Policyファイルの作成(オプション)

信頼性のあるメッセージングおよび接続作成ポリシー・アサーションの詳細は、次を参照してください。

- 『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスの信頼性のあるメッセージングのポリシー・アサーションのリファレンスに関する項

- 『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebサービスの接続作成ポリシー・アサーションのリファレンスに関する項

次の表に、あらかじめパッケージ化されたWS-Policyファイルをまとめます。この表は、WS-Policyファイルをメソッド・レベルでアタッチできるかどうかも指定します。この列の値が「No」の場合、WS-Policyファイルをクラス・レベルでのみアタッチできます。

表A-1 信頼性のあるメッセージングをサポートする、あらかじめパッケージ化されているWS-Policyファイル

あらかじめパッケージ化されているWS-Policyファイル

説明

メソッド・レベルのアタッチ

DefaultReliability1.2.xml

配信保証に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702のWS Reliable Messaging Policy Assertion 1.2が基になっています。「DefaultReliability1.2.xml (WS-Policyファイル)」を参照してください。

はい

DefaultReliability1.1.xml

サービス品質に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。「DefaultReliability1.1.xml (WS-Policyファイル)」を参照してください。

はい

DefaultRelibility.xml

非推奨。Webサービスの信頼性のあるメッセージングのアサーションは、WS Reliable Messaging Policy Assertion Version 1.0(http://schemas.xmlsoap.org/ws/2005/02/rm/WS-RMPolicy.pdf)に基づいています。このリリースでは、信頼性のあるメッセージングのポリシー・アサーションの多くが、JWSアノテーションまたは構成を通じて管理されます。

信頼性のあるメッセージングのポリシー・アサーションに一般的な値(非アクティブ・タイムアウト10分、確認応答の間隔200ミリ秒、基本的な再送信間隔3秒など)を指定します。「DefaultReliability.xml WS-Policyファイル(WS-Policy)[非推奨]」を参照してください。

はい

LongRunningReliability.xml

非推奨。長期実行プロセスに関して、Webサービスの信頼性のあるメッセージングのアサーションは、WS Reliable Messaging Policy Assertion Version 1.0に基づいています。このリリースでは、信頼性のあるメッセージングのポリシー・アサーションの多くが、JWSアノテーションまたは構成を通じて管理されます。

1つ前に示した、信頼性のあるメッセージングのデフォルトWS-Policyファイルとほぼ同じですが、アクティビティのタイムアウト間隔に、より大きな値(24時間)を指定する点が異なります。「LongRunningReliability.xml WS-Policyファイル(WS-Policy)[非推奨]」を参照してください。

はい

Mc1.1.xml

Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。WS-Policy 1.5プロトコルが使用されます。「Mc1.1.xml (WS-Policyファイル)」を参照してください。

いいえ

Mc.xml

Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。WS-Policy 1.2プロトコルが使用されます。「Mc.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.2_ExactlyOnce_WithMC1.1.xml

サービス品質に関するポリシー・アサーションを指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。「Reliability1.2_ExactlyOnce_WithMC1.1.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.2_SequenceSTRSecurity

信頼性のあるシーケンスでメッセージを保護するために、CreateSequenceメッセージで参照されるwsse:SecurityTokenReferenceをランタイムが使用するように指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702のWS Reliable Messaging Policy Assertion 1.2が基になっています。「Reliability1.2_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.1_SequenceSTRSecurity

Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。「Reliability1.1_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.2_SequenceTransportSecurity

トランスポート・レベルのセキュリティとサービス品質に関連するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702のWS Reliable Messaging Policy Assertion 1.2が基になっています。「Reliability1.2_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.1_SequenceTransportSecurity

トランスポート・レベルのセキュリティとサービス品質に関連するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。「Reliability1.1_SequenceTransportSecurity.xml (WS-Policyファイル)」を参照してください。

はい

Reliability1.0_1.2.xml

1.2と1.0のWS-Reliableメッセージング・ポリシー・アサーションを結合します。1.2バージョンのポリシー・アサーションはWebサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。このサンプルは、適切なポリシーの選択に基づいて実行時に適用されるポリシー・アサーションを決定します。「Reliability1.0_1.2.xml (WS-Policyファイル)」を参照してください。

いいえ

Reliability1.0_1.1.xml

1.1と1.0のWS Reliable Messagingポリシー・アサーションを結合します。「Reliability1.0_1.1.xml (WS-Policy.xmlファイル)」を参照してください。

はい

DefaultReliability1.2.xml (WS-Policyファイル)

DefaultRealiability1.2.xml WS-Policyファイルは、配信保証に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.2-spec-os.htmlのWS Reliable Messaging Policy Assertion 1.2が基になっています。

<?xml version="1.0" encoding="UTF-8"?>
<wsp15:Policy xmlns:wsp15="http://www.w3.org/ns/ws-policy">
<wsp15:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:DeliveryAssurance>
<wsp15:Policy>
<wsrmp:ExactlyOnce/>
<wsrmp:InOrder/>
</wsp15:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp15:All>
</wsp15:Policy>

DefaultReliability1.1.xml (WS-Policyファイル)

DefaultRealiability1.1.xml WS-Policyファイルは、サービス品質に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。

<?xml version="1.0"?>

<wsp:Policy
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702"
>
<wsrmp:DeliveryAssurance>
<wsp:Policy>
<wsrmp:ExactlyOnce />
</wsp:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp:Policy>

DefaultReliability.xml WS-Policyファイル(WS-Policy)[非推奨]

このWS-Policyファイルは非推奨となっています。Webサービスの信頼性のあるメッセージングのアサーションは、WS Reliable Messaging Policy Assertion Version 1.0(http://schemas.xmlsoap.org/ws/2005/02/rm/policy/)に基づいています。現在のリリースでは、信頼性のあるメッセージングのポリシー・アサーションの多くが、JWSアノテーションまたは構成を通じて管理されます。

DefaultReliability.xml WS-Policyファイルは、信頼性のあるメッセージングのポリシーのアサーションに一般的な値(非アクティブ・タイムアウト10分、確認応答の間隔200ミリ秒、基本的な再送信間隔3秒など)を指定します。

<?xml version="1.0"?>

<wsp:Policy
xmlns:wsrm="http://schemas.xmlsoap.org/ws/2005/02/rm/policy"
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
xmlns:beapolicy="http://www.bea.com/wsrm/policy"
>

<wsrm:RMAssertion >
<wsrm:InactivityTimeout Milliseconds="600000" />
<wsrm:BaseRetransmissionInterval Milliseconds="3000" />
<wsrm:ExponentialBackoff />
<wsrm:AcknowledgementInterval Milliseconds="200" />
<beapolicy:Expires Expires="P1D" optional="true"/>
</wsrm:RMAssertion>
</wsp:Policy>

LongRunningReliability.xml WS-Policyファイル(WS-Policy)[非推奨]

このWS-Policyファイルは非推奨となっています。Webサービスの信頼性のあるメッセージングのアサーションは、WS Reliable Messaging Policy Assertion Version 1.0(http://schemas.xmlsoap.org/ws/2005/02/rm/policy/)に基づいています。現在のリリースでは、信頼性のあるメッセージングのポリシー・アサーションの多くが、JWSアノテーションまたは構成を通じて管理されます。

LongRunningRelibility.xml WS-Policyファイルは、DefaultReliability.xml WS-Policyファイルと同じような値を指定しますが、指定するアクティビティのタイムアウト間隔がより長い(24時間)点が異なります。「LongRunningReliability.xml WS-Policyファイル(WS-Policy)[非推奨]」を参照してください。

<?xml version="1.0"?>

<wsp:Policy
xmlns:wsrm="http://schemas.xmlsoap.org/ws/2005/02/rm/policy"
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
xmlns:beapolicy="http://www.bea.com/wsrm/policy"
>
<wsrm:RMAssertion >
<wsrm:InactivityTimeout Milliseconds="86400000" />
<wsrm:BaseRetransmissionInterval Milliseconds="3000" />
<wsrm:ExponentialBackoff />
<wsrm:AcknowledgementInterval Milliseconds="200" />
<beapolicy:Expires Expires="P1M" optional="true"/>
</wsrm:RMAssertion>
</wsp:Policy>

Mc1.1.xml (WS-Policyファイル)

Mc1.1.xml WS-Policyファイルは、Webサービスにおける接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を設定します。この場合、WS-Policy 1.5プロトコルが使用されます。アサーションは、http://docs.oasis-open.org/ws-rx/wsmc/200702/wsmc-1.1-spec-os.htmlに定義されている接続作成ポリシー・アサーションに基づいています。

<?xml version="1.0"?>
<wsp15:Policy
xmlns:wsp15="http://www.w3.org/ns/ws-policy"
xmlns:wsmc="http://docs.oasis-open.org/ws-rx/wsmc/200702">
<wsmc:MCSupported wsp15:Optional="true" />
</wsp15:Policy>

Mc.xml (WS-Policyファイル)

Mc.xml WS-Policyファイルは、Webサービスにおける接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を設定します。アサーションは、http://docs.oasis-open.org/ws-rx/wsmc/200702/wsmc-1.1-spec-os.htmlに定義されている接続作成ポリシー・アサーションに基づいています。

<?xml version="1.0"?>
<wsp:Policy
xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy"
xmlns:wsmc="http://docs.oasis-open.org/ws-rx/wsmc/200702">
<wsmc:MCSupported wsp:Optional="true" />
</wsp:Policy>

Reliability1.2_ExactlyOnce_WithMC1.1.xml (WS-Policyファイル)

Reliability1.2_ExactlyOnce_WithMC1.1.xml WS-Policyファイルは、サービス品質に関するポリシー・アサーションを指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。

アサーションは、次の仕様に基づいています。

- Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.2-spec-os.htmlのWS Reliable Messaging Policy Assertion 1.2に基づいています。

- 接続作成アサーションは、http://docs.oasis-open.org/ws-rx/wsmc/200702/wsmc-1.1-spec-os.htmlに定義されている接続作成ポリシー・アサーションに基づいています。

<?xml version="1.0" encoding="UTF-8" ?>
<wsp15:Policy xmlns:wsp15="http://www.w3.org/ns/ws-policy">
<wsp15:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:DeliveryAssurance>
<wsp15:Policy>
<wsrmp:ExactlyOnce />
</wsp15:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
<wsmc:MCSupported
xmlns:wsmc="http://docs.oasis-open.org/ws-rx/wsmc/200702"
wsp15:Optional="true" />
</wsp15:All>
</wsp15:Policy>

Reliability1.2_SequenceSTR.xml (WS-Policyファイル)

Reliability1.2_SequenceSTR.xmlファイルは、信頼性のあるシーケンスでメッセージを保護するために、CreateSequenceメッセージで参照されるwsse:SecurityTokenReferenceをランタイムが使用するように指定します。Webサービスでの接続作成のサポートを有効にし、オプションとしてWebサービス・クライアントでの使用方法を指定します。

アサーションは、次の仕様に基づいています。

- Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.2-spec-os.htmlのWS Reliable Messaging Policy Assertion 1.2に基づいています。

- 接続作成アサーションは、http://docs.oasis-open.org/ws-rx/wsmc/200702/wsmc-1.1-spec-os.htmlに定義されている接続作成ポリシー・アサーションに基づいています。

<?xml version="1.0" encoding="UTF-8"?>
<wsp15:Policy xmlns:wsp15="http://www.w3.org/ns/ws-policy">
<wsp15:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:SequenceSTR/>
<wsrmp:DeliveryAssurance>
<wsp15:Policy>
<wsrmp:ExactlyOnce/>
</wsp15:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
<wsmc:MCSupported
xmlns:wsmc="http://docs.oasis-open.org/ws-rx/wsmc/200702"
wsp15:Optional="true"/>
</wsp15:All>
</wsp15:Policy>

Reliability1.1_SequenceSTR.xml (WS-Policyファイル)

Reliability1.1_SequenceSTR.xmlファイルは、信頼性のあるシーケンスでメッセージを保護するために、CreateSequenceメッセージで参照されるwsse:SecurityTokenReferenceをランタイムが使用するように指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。

<wsp:Policy xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:SequenceSTR/>
<wsrmp:DeliveryAssurance>
<wsp:Policy>
<wsrmp:ExactlyOnce/>
</wsp:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp:Policy>

Reliability1.2_SequenceTransportSecurity.xml (WS-Policyファイル)

Reliability1.2_SequenceTransportSecurity.xmlファイルは、トランスポート・レベルのセキュリティおよびサービス品質に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrm/200702/wsrm-1.2-spec-os.htmlのWS Reliable Messaging Policy Assertion 1.2が基になっています。

<?xml version="1.0" encoding="UTF-8"?>
<wsp15:Policy xmlns:wsp15="http://www.w3.org/ns/ws-policy">
<wsp15:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:SequenceTransportSecurity/>
<wsrmp:DeliveryAssurance>
<wsp15:Policy>
<wsrmp:ExactlyOnce/>
</wsp15:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp15:All>
</wsp15:Policy>

Reliability1.1_SequenceTransportSecurity.xml (WS-Policyファイル)

Reliability1.1_SequenceTransportSecurity.xmlファイルは、トランスポート・レベルのセキュリティおよびサービス品質に関するポリシー・アサーションを指定します。Webサービスの信頼性のあるメッセージング・アサーションは、http://docs.oasis-open.org/ws-rx/wsrmp/200702/wsrmp-1.1-spec-os-01.htmlのWS Reliable Messaging Policy Assertion 1.1が基になっています。

<wsp:Policy xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:SequenceTransportSecurity/>
<wsrmp:DeliveryAssurance>
<wsp:Policy>
<wsrmp:ExactlyOnce/>
</wsp:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp:Policy>

Reliability1.0_1.2.xml (WS-Policyファイル)

Reliability1.0_1.2.xml WS-Policyファイルは、1.2および1.0のWS-信頼性のあるメッセージングのポリシー・アサーションを結合します。

このサンプルは、適切なポリシーの選択に基づいて実行時に適用されるポリシー・アサーションを決定します。適切なポリシーの選択の詳細は、「複数のポリシー選択肢の使用」を参照してください。

<?xml version="1.0" encoding="UTF-8"?>
<wsp15:Policy xmlns:wsp15="http://www.w3.org/ns/ws-policy">
<wsp15:ExactlyOne>
<wsp15:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:DeliveryAssurance>
<wsp15:Policy>
<wsrmp:ExactlyOnce/>
</wsp15:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
<wsmc:MCSupported
xmlns:wsmc="http://docs.oasis-open.org/ws-rx/wsmc/200702"
wsp15:Optional="true"/>
</wsp15:All>
<wsp15:All>
<wsrmp10:RMAssertion
xmlns:wsrmp10="http://schemas.xmlsoap.org/ws/2005/02/rm/policy">
<wsrmp10:InactivityTimeout Milliseconds="600000"/>
<wsrmp10:BaseRetransmissionInterval Milliseconds="3000"/>
<wsrmp10:ExponentialBackoff/>
<wsrmp10:AcknowledgementInterval Milliseconds="200"/>
</wsrmp10:RMAssertion>
</wsp15:All>
</wsp15:ExactlyOne>
</wsp15:Policy>

Reliability1.0_1.1.xml (WS-Policy.xmlファイル)

Reliability1.0_1.1.xml WS-Policyファイルは、1.1および1.0のWS-信頼性のあるメッセージングのポリシー・アサーションを結合します。このサンプルは、適切なポリシーの選択に基づいて実行時に適用されるポリシー・アサーションを決定します。適切なポリシーの選択の詳細は、「複数のポリシー選択肢の使用」を参照してください。

注意:
1.0のWebサービスの信頼性のあるメッセージング・アサーションには、接頭辞としてwsrmp10が付加されます。

<wsp:Policy xmlns:wsp="http://schemas.xmlsoap.org/ws/2004/09/policy">
<wsp:ExactlyOne>
<wsp:All>
<wsrmp:RMAssertion
xmlns:wsrmp="http://docs.oasis-open.org/ws-rx/wsrmp/200702">
<wsrmp:DeliveryAssurance>
<wsp:Policy>
<wsrmp:ExactlyOnce/>
</wsp:Policy>
</wsrmp:DeliveryAssurance>
</wsrmp:RMAssertion>
</wsp:All>
<wsp:All>
<wsrmp10:RMAssertion
xmlns:wsrmp10="http://schemas.xmlsoap.org/ws/2005/02/rm/policy">
<wsrmp10:InactivityTimeout Milliseconds="600000"/>
<wsrmp10:BaseRetransmissionInterval Milliseconds="3000"/>
<wsrmp10:ExponentialBackoff/>
<wsrmp10:AcknowledgementInterval Milliseconds="200"/>
</wsrmp10:RMAssertion>
</wsp:All>
</wsp:ExactlyOne>
</wsp:Policy>

B 信頼性のあるメッセージングのバッチ化のためのクライアント・ラッパー・クラスの例

この付録では、Java API for XML Web Services (JAX-WS)を使用したWebLogic Server 12.1.3用のWebLogic Webサービスで、信頼性のあるメッセージングのバッチ処理に使用できるクライアント・ラッパー・クラスの例を示します。

信頼性のあるメッセージングのバッチ化の詳細は、「ビジネス作業単位へのメッセージのグループ化(バッチ化)」を参照してください。

注意:
このクライアント・ラッパー・クラスはサンプル・コードです。正式にサポートされている製品クラスではありません。

例B-1 信頼性のあるメッセージングのバッチ化のためのクライアント・ラッパー・クラスの例

package example.servlet;

import java.io.PrintStream;
import java.io.PrintWriter;
import java.lang.ref.WeakReference;
import java.lang.reflect.InvocationHandler;
import java.lang.reflect.Method;
import java.lang.reflect.Proxy;
import java.util.Date;
import java.util.SortedSet;
import java.util.Timer;
import java.util.TimerTask;

import javax.xml.datatype.DatatypeFactory;
import javax.xml.datatype.Duration;
import javax.xml.ws.BindingProvider;

import weblogic.wsee.jaxws.JAXWSProperties;
import weblogic.wsee.jaxws.spi.ClientInstance;
import weblogic.wsee.reliability.MessageRange;
import weblogic.wsee.reliability2.api.WsrmClient;
import weblogic.wsee.reliability2.api.WsrmClientFactory;
import weblogic.wsee.reliability2.property.WsrmInvocationPropertyBag;
import weblogic.wsee.reliability2.tube.WsrmClientImpl;

/**
* Example wrapper class to batch reliable requests into fixed size 'batches'
* that can be sent using a single RM sequence. This class allows a client to
* send requests that have no natural common grouping or
* 'business unit of work' and not pay the costs associated with creating and
* terminating an RM sequence for every message.
* NOTE: This class is an *example* of how batching might be performed. To do
*       batching correctly, you should consider error recovery and how to
*       report sequence errors (reported via ReliabilityErrorListener) back
*       to the clients that made the original requests.
* <p>
* If your web service client code knows of some natural business-oriented
* grouping of requests (called a 'business unit of work'), it should make the
* RM subsystem aware of this unit of work by using the
* WsrmClient.setFinalMessage() method to demarcate the end of a unit (just
* before sending the actual final request via an invocation on
* the client instance). In some cases, notably when the client code represents
* an intermediary in the processing of messages, the client code may not be
* aware of any natural unit of work. In the past, if no business unit of work
* could be determined, clients often just created the client instance, sent the
* single current message they had, and then allowed the sequence to terminate.
* This is functionally workable, but very inefficient. These clients pay the
* cost of an RM sequence handshake and termination for every message they send.
* The BatchingRmClientWrapper class can be used to introduce an artificial
* unit of work (a batch) when no natural business unit of work is available.
* <p>
* Each instance of BatchingRmClientWrapper is a wrapper instance around a
* client instance (port or Dispatch instance). This wrapper can be used to
* obtain a Proxy instance that can be used in place of the original client
* instance. This allows this class to perform batching operations completely
* invisibly from the perspective of the client code.
* <p>
* This class is used for batching reliable requests into
* batches of a given max size that will survive for a given maximum
* duration. If a batch fills up or times out, it is ended, causing the
* RM sequence it represents to be ended/terminated. The timeout ensures that
* if the flow of incoming requests stops the batch/sequence will still
* end in a timely manner.
*/
public class BatchingRmClientWrapper<T>
implements InvocationHandler {

private Class<T> _clazz;
private int _batchSize;
private long _maxBatchLifetimeMillis;
private T _clientInstance;
private PrintWriter _out;
private WsrmClient _rmClient;
private int _numInCurrentBatch;
private int _batchNum;
private Timer _timer;
private boolean _closed;
private boolean _proxyCreated;

/**
* Create a wrapper instance for batching reliable requests into
* batches of the given max size that will survive for the given maximum
* duration. If a batch fills up or times out, it is ended, causing the
* RM sequence it represents to be ended/terminated.
* @param clientInstance The client instance that acts as the source object
*        for the batching proxy created by the createProxy() method. This
*        is the port/Dispatch instance returned from the call to
*        getPort/createDispatch. The BatchingRmClientWrapper will take over
*        responsibility for managing the interaction with and cleanup of
*        the client instance via the proxy created from createProxy.
* @param clazz of the proxy instance we'll be creating in createProxy.
*        This should be the class of the port/Dispatch instance you would
*        use to invoke operations on the service. BatchingRmClientWrapper will
*        create (via createProxy) a proxy of the given type that can be
*        used in place of the original client instance.
* @param batchSize Max number of requests to put into a batch. If the
*        max number of requests are sent for a given batch, that batch is
*        ended (ending/terminating the sequence it represents) and a new
*        batch is started.
* @param maxBatchLifetime A duration value (in the lexical form supported
*        by java.util.Duration, e.g. PT30S for 30 seconds) representing
*        the maximum time a batch should exist. If the batch exists longer
*        than this time, it is ended and a new batch is begun.
* @param out A print stream that can be used to print diagnostic and
*        status messages.
*/
public BatchingRmClientWrapper(T clientInstance, Class<T> clazz,
int batchSize, String maxBatchLifetime,
PrintStream out) {
_clazz = clazz;
_batchSize = batchSize;
try {
if (maxBatchLifetime == null) {
maxBatchLifetime = "PT5M";
}
Duration duration =
DatatypeFactory.newInstance().newDuration(maxBatchLifetime);
_maxBatchLifetimeMillis = duration.getTimeInMillis(new Date());
} catch (Exception e) {
throw new RuntimeException(e.toString(), e);
}
_clientInstance = clientInstance;
_out = new PrintWriter(out, true);
_rmClient = WsrmClientFactory.getWsrmClientFromPort(_clientInstance);
_closed = false;
_proxyCreated = false;
_timer = new Timer(true);
_timer.schedule(new TimerTask() {
@Override
public void run() {
terminateOrEndBatch();
}
}, _maxBatchLifetimeMillis);
}

/**
* Creates the dynamic proxy that should be used in place of the client
* instance used to create this BatchingRmClientWrapper instance. This method
* should be called only once per BatchingRmClientWrapper.
*/
public T createProxy() {
if (_proxyCreated) {
throw new IllegalStateException("Already created the proxy for this BatchingRmClientWrapper
instance which wraps the client instance: " + _clientInstance);
}
_proxyCreated = true;
return (T) Proxy.newProxyInstance(getClass().getClassLoader(),
new Class[] {
_clazz,
BindingProvider.class,
java.io.Closeable.class
}, this);
}

private void terminateOrEndBatch() {
synchronized(_clientInstance) {
if (_rmClient.getSequenceId() != null) {
if (terminateBatchAllowed()) {
_out.println("Terminating batch " + _batchNum + " sequence (" + _
rmClient.getSequenceId() + ") for " + _clientInstance);
try {
_rmClient.terminateSequence();
} catch (Exception e) {
e.printStackTrace(_out);
}
} else {
_out.println("Batch " + _batchNum + " sequence (" + _rmClient.getSequenceId() + ")
for " + _clientInstance + " timed out but has outstanding requests to send and
cannot be terminated now");
}
}
endBatch();
}
}

/**
* Check to see if we have acks for all requests sent. If so,
* we can terminate.
*/
private boolean terminateBatchAllowed() {
try {
synchronized(_clientInstance) {
if (_rmClient.getSequenceId() != null) {
long maxMsgNum = _rmClient.getMostRecentMessageNumber();
if (maxMsgNum < 1) {
// No messages sent, go ahead and terminate.
return true;
}
SortedSet<MessageRange> ranges = _rmClient.getAckRanges();
long maxAck = -1;
boolean hasGaps = false;
long lastRangeUpper = -1;
for (MessageRange range: ranges) {
if (lastRangeUpper > 0) {
if (range.lowerBounds != lastRangeUpper + 1) {
hasGaps = true;
}
} else {
lastRangeUpper = range.upperBounds;
}
maxAck = range.upperBounds;
}
return !(hasGaps || maxAck < maxMsgNum);
}
}
} catch (Exception e) {
e.printStackTrace(_out);
}
return true;
}

private void endBatch() {
synchronized(_clientInstance) {
if (_numInCurrentBatch > 0) {
_out.println("Ending batch " + _batchNum + " sequence (" + _rmClient.getSequenceId() + ")
for " + _clientInstance + "...");
}
/**
* _rmClient.reset() resets a WsrmClient instance (and the client instance it represents)
* so it can track a new WS-RM sequence for the next invoke on the client
* instance. This method effectively *disconnects* the RM sequence from the
* client instance and lets them continue/complete separately.
*/
_rmClient.reset();
_numInCurrentBatch = 0;
if (!_closed) {
_timer.schedule(new TimerTask() {
@Override
public void run() {
terminateOrEndBatch();
}
}, _maxBatchLifetimeMillis);
}
}
}

public Object invoke(Object proxy, Method method, Object[] args)
throws Throwable {
boolean operationInvoke = method.getDeclaringClass() == _clazz;
boolean closeableInvoke = method.getDeclaringClass() ==
java.io.Closeable.class;
boolean endOfBatch = false;
if (operationInvoke) {
synchronized(_clientInstance) {
// Check our batch size
if (_numInCurrentBatch == 0) {
_batchNum++;
}
endOfBatch = _numInCurrentBatch >= _batchSize - 1;
if (endOfBatch) {
_rmClient.setFinalMessage();
}
_out.println("Making " + (endOfBatch ? "final " : "") + "invoke " +
(_numInCurrentBatch+1) + " of batch " + _batchNum + " sequence (" + _
rmClient.getSequenceId() + ") with operation: " + method.getName());
}
} else if (closeableInvoke && method.getName().equals("close")) {
synchronized(_clientInstance) {
// Make sure we don't try to schedule the timer anymore
_closed = true;
_timer.cancel();
}
}
Object ret = method.invoke(_clientInstance, args);
if (operationInvoke) {
synchronized(_clientInstance) {
_numInCurrentBatch++;
if (endOfBatch) {
endBatch();
}
}
}
return ret;
}
}

C JAX-WSへのJAX-RPC Webサービスおよびクライアントの移行

この付録では、WebLogic Server 12.1.3のJava API for XML-based RPC (JAX-RPC) WebサービスおよびクライアントをXML-based Web services (JAX-WS)に移行する方法について説明します。

JAX-RPC Webサービスを移行する場合、JAX-RPC Webサービスを生成するには、WSDLファイルから、トップダウンのアプローチを使用して元のWSDLファイルを保存します。詳細は、「WSDLファイルから開始するWebLogic Webサービスの開発: 主な手順」を参照してください。

注意:
JAX-WSでJAX-RPCの機能がサポートされていない場合があります。この場合は、アプリケーションを再構築しないと移行できません。

次の表に、説明するトピックをまとめます。

表C-1 JAX-RPCのWebサービスおよびクライアントをJAX-WSへ移行するためのヒント

トピック

説明

WebLogic Webサービスの最終コンテキスト・ルートの設定

WebLogic Webサービスの最終コンテキスト・ルートの設定方法を説明します。JAX-WSでは@WLXXXTransport JWSアノテーションの使用がサポートされていません。これらのアノテーションはJAX-RPCでのみサポートされます。

WebLogic独自のアノテーションの使用

JAX-WSでサポートされるWebLogic独自のアノテーションについて説明します。

WSDLファイルの生成

jwsc Antタスクを使用してJAX-WS Webサービスを生成する際にWSDLファイルを生成する方法を説明します。

JAXBカスタム・タイプの使用

すべてのデータ・バインディング・タスクを管理するためのJava Architecture for XML Binding (JAXB)の使用について説明します。

EJB 3.0の使用

EJB 2.1からのEJB 3.0における変更点について説明します。JAX-WSはEJB 3.0をサポートします。JAX-RPCはEJB 2.1のみをサポートします。

RPCスタイルSOAPバインディングからの移行

SOAPバインディングを設定するためのガイドラインについて説明します。RPC形式はサポートされますが、JAX-WSでは推奨されません。

SOAPメッセージ・ハンドラの更新

JAX-WSへの移行時に、現在のJAX-RPC SOAPメッセージ・ハンドラを書き直さなければならない点について説明します。

JAX-WSクライアントの呼出し

JAX-WSクライアントを呼び出すようにJAX-RPCクライアントを書き直さなければならない点について説明します。

WebLogic Webサービスの最終コンテキスト・ルートの設定

WebLogic Webサービスの最終的なコンテキスト・ルートは、様々な方法で設定できます。『Oracle WebLogic Server JAX-RPC Webサービスの開発』のWebサービスの呼出しに使用されるトランスポートの指定に関する項を参照してください。

この項で説明するように、JAX-RPC Webサービスを定義する際は、@WLXXXTransport JWSアノテーションを使用してコンテキスト・ルートを指定できます。この@WLXXXTransport JWSアノテーションは、JAX-WS Webサービスには無効です。JAX-RPC Webサービスで使用する場合、他の方法の1つを使用するためにこのアノテーションを削除してJWSファイルを更新する必要があります。

WebLogic独自のアノテーションの使用

JAX-WSでは以下のWebLogic独自のアノテーションがサポートされています。

- @Policy

- @Policies

- @SecurityPolicy

- @SecurityPolicies

- @WssConfiguration

その他のWebLogic固有のアノテーションは、JAX-WSへの移行時にJAX-RPCアプリケーションからすべて削除する必要があります。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のWebLogic固有のアノテーションに関する項を参照してください。

WSDLファイルの生成

JAX-RPC Webサービスでjwscファイルを実行すると、指定した出力ディレクトリにWSDLファイルが生成されます。JAX-WS Webサービスの場合、WSDLファイルはサービス・エンドポイントのデプロイ時に生成されます。WSDLファイルを出力ディレクトリに生成するには、jwsc Antタスクの<jws子要素でwsdlOnly属性を指定する必要があります。詳細は、『Oracle WebLogic Server WebLogic Webサービス・リファレンス』のjwscに関する項を参照してください。

JAXBカスタム・タイプの使用

JAX-WSでは、Java Architecture for XML Binding (JAXB) (http://jcp.org/en/jsr/detail?id=222を参照)を使用してあらゆるデータ・バインディング・タスクを管理します。アプリケーションでXMLBeanまたはTylarを使用してカスタム・タイプをサポートしている場合、JAXBを使用するようにそれらを変更する必要があります。JAXBを使用する方法の詳細は、第5章「JAXBデータ・バインディングの使用」を参照してください。

EJB 3.0の使用

JAX-WSはEJB 3.0をサポートします。JAX-RPCはEJB 2.1のみをサポートします。

EJB 3.0では、EJBを実装する場合に必要なEJBリモートおよびホーム・インタフェース・クラスおよびデプロイメント記述子ファイルを、手動で作成するのではなく、自動的に生成することができるメタデータ・アノテーションが導入されました。

EJB 3.0 Beanクラス要件および2.xからの変更点については、『Oracle WebLogic Server Enterprise JavaBeansの開発』のBeanファイルのプログラミング: 要件および2.Xからの変更点に関する項を参照してください。

RPCスタイルSOAPバインディングからの移行

SOAPBinding.Style.RPCスタイルの使用はサポートされていますが、JAX-WSでは推奨されません。このスタイルはSOAPBinding.Style.DOCUMENTへ変更するようお薦めします。

SOAPメッセージ・ハンドラの更新

SOAP APIは似ていますが、JAX-RPC SOAPハンドラは、JAX-WSで動作するよう変更する必要があります。詳細は、第25章「SOAPヘッダーの送受信」を参照してください。

JAX-WSクライアントの呼出し

JAX-RPCとJAX-WSのクライアントAPIは完全に異なるため、JAX-RPCクライアントを書き直す必要があります。JAX-WSクライアントの開発の詳細は、『Oracle WebLogic Server 12.1.3 JAX-WS Webサービスの開発』のWebサービス・クライアントの開発に関する項を参照してください。

オラクル社の法律上の注意点について

コピーライトについて

Copyright © 1994-2015, Oracle and/or its affiliates.All rights reserved.

商標と登録商標について

OracleおよびJavaはOracle Corporationおよびその関連企業の登録商標です。その他の名称は、それぞれの所有者の商標または登録商標です。

Intel、Intel Xeonは、Intel Corporationの商標または登録商標です。すべてのSPARCの商標はライセンスをもとに使用し、SPARC International, Inc.の商標または登録商標です。AMD、Opteron、AMDロゴ、AMD Opteronロゴは、Advanced Micro Devices, Inc.の商標または登録商標です。UNIXは、The Open Groupの登録商標です。

ライセンス制約の保証と結果的に生じる損害の免責

このソフトウェアおよび関連ドキュメントの使用と開示は、ライセンス契約の制約条件に従うものとし、知的財産に関する法律により保護されています。ライセンス契約で明示的に許諾されている場合もしくは法律によって認められている場合を除き、形式、手段に関係なく、いかなる部分も使用、複写、複製、翻訳、放送、修正、ライセンス供与、送信、配布、発表、実行、公開または表示することはできません。このソフトウェアのリバース・エンジニアリング、逆アセンブル、逆コンパイルは互換性のために法律によって規定されている場合を除き、禁止されています。

保証免責

ここに記載された情報は予告なしに変更される場合があります。また、誤りが無いことの保証はいたしかねます。誤りを見つけた場合は、オラクル社までご連絡ください。

制限付権利

このソフトウェアまたは関連ドキュメントを、米国政府機関もしくは米国政府機関に代わってこのソフトウェアまたは関連ドキュメントをライセンスされた者に提供する場合は、次の通知が適用されます。

U.S. GOVERNMENT END USERS: Oracle programs, including any operating system, integrated software, any programs installed on the hardware, and/or documentation, delivered to U.S. Government end users are "commercial computer software" pursuant to the applicable Federal Acquisition Regulation and agency-specific supplemental regulations.As such, use, duplication, disclosure, modification, and adaptation of the programs, including any operating system, integrated software, any programs installed on the hardware, and/or documentation, shall be subject to license terms and license restrictions applicable to the programs.No other rights are granted to the U.S. Government.

危険な用途への使用について

このソフトウェアもしくはハードウェアは様々な情報管理アプリケーションでの一般的な使用のために開発されたものです。このソフトウェアもしくはハードウェアは、危険が伴うアプリケーション（人的傷害を発生させる可能性があるアプリケーションを含む）への用途を目的として開発されていません。このソフトウェアもしくはハードウェアを危険が伴うアプリケーションで使用する際、安全に使用するために、適切な安全装置、バックアップ、冗長性（redundancy）、その他の対策を講じることは使用者の責任となります。このソフトウェアもしくはハードウェアを危険が伴うアプリケーションで使用したことに起因して損害が発生しても、オラクル社およびその関連会社は一切の責任を負いかねます。

第三者のコンテンツ、製品、サービスに対する免責事項

このソフトウェアまたはハードウェア、そしてドキュメントは、第三者のコンテンツ、製品、サービスへのアクセス、あるいはそれらに関する情報を提供することがあります。オラクル社およびその関連会社は、第三者のコンテンツ、製品、サービスに関して一切の責任を負わず、いかなる保証もいたしません。オラクル社およびその関連会社は、第三者のコンテンツ、製品、サービスへのアクセスまたは使用によって損失、費用、あるいは損害が発生しても一切の責任を負いかねます。

ドラフトのアルファ版およびベータ版ドキュメントについて

このドキュメントが試作版の場合:

このドキュメントは試作版であり、デモおよび暫定使用のみを目的としたものです。このソフトウェアを使用するハードウェアに限定するものではありません。オラクル社およびその関連会社は、このドキュメントに関して一切の責任を負わず、いかなる保証もいたしません。また、このドキュメントを使用したことによって損失、費用、あるいは損害が発生しても、一切の責任を負いかねます。