目次 前 次 PDF


Oracle Tuxedo CORBAサーバー・アプリケーションの作成手順

Oracle Tuxedo CORBAサーバー・アプリケーションの作成手順
この章では、CORBAサーバー・アプリケーションを作成する基本的なステップについて説明します。この章で示されるステップは確定的ではありません。特定のサーバー・アプリケーションでは他のステップを踏む必要がある可能性もあり、一部のステップの順序を変更する必要がある場合もあります。ただし、すべてのCORBAサーバー・アプリケーションの開発プロセスでは、共通してこれらのステップを使用します。
このトピックには次の項が含まれます:
この章では、最初にステップの概要を示し、このマニュアル全体を通して使用される開発ツールとコマンドのリストを示します。特定のデプロイメント環境では追加のソフトウェア開発ツールを使用する場合があるため、この章でリストおよび説明しているツールとコマンドも確定的ではありません。
この章では、Oracle Tuxedoソフトウェアに用意されているBasic Universityサンプル・アプリケーションの例を使用します。Basic Universityサンプル・アプリケーションの詳細は、『CORBA Universityサンプル・アプリケーション・ガイド』を参照してください。このマニュアル全体を通して使用されるツールとコマンドの詳細は、『CORBAプログラミング・リファレンス』を参照してください。
マルチスレッドCORBAサーバー・アプリケーションの作成の詳細は、第4章「マルチスレッドCORBAサーバー・アプリケーションの作成」を参照してください。
CORBAサーバー・アプリケーション開発プロセスのサマリー
サーバー・アプリケーションを作成する基本的なステップは、次のとおりです。
ステップ1: サーバー・アプリケーション用のOMG IDLファイルのコンパイル
ステップ2: 各インタフェースの操作を実装するメソッドの記述
ステップ3: サーバー・オブジェクトの作成
ステップ4: メモリー内でのオブジェクトの振る舞いの定義
ステップ5: サーバー・アプリケーションのコンパイルとリンク
ステップ6: サーバー・アプリケーションのデプロイ
Oracle Tuxedoソフトウェアには、表2-1に示す開発ツールとコマンドも用意されています。
 
TUXCONFIGファイルを作成します(このファイルは、サーバー・アプリケーションの構成を指定するCORBAドメインのバイナリ・ファイルです)。
ステップ1:サーバー・アプリケーション用のOMG IDLファイルのコンパイル
Oracle Tuxedoドメインで実行されるアプリケーションのクライアント部分とサーバー部分の基本構造は、アプリケーションのOMG IDLファイルの文によって決定されます。アプリケーションのOMG IDLファイルをコンパイルすると、IDLコンパイラは、idlコマンドで指定したオプションに応じて、次の図に示すファイルの一部またはすべてを生成します。共有コンポーネントは、サーバー・アプリケーションを作成するために修正する生成済ファイルです。
表2-2に、IDLコンパイラで生成されるファイルの説明を示します
 
IDLコンパイラの使い方
表2-1にリストされているファイルを生成するには、次のコマンドを入力します。
idl [options] idl-filename [icf-filename]
idlコマンド構文の意味は次のとおりです。
optionsは、IDLコンパイラへの1つ以上のコマンド行オプションを表します。コマンド行オプションについては、『CORBAプログラミング・リファレンス』で説明されています。実装ファイルを生成する場合は、-iオプションを指定する必要があります。
idl-filenameは、アプリケーションのOMG IDLファイルの名前を表します。
icf-filenameは、アプリケーションの実装構成ファイル(ICFファイル)の名前を表すオプション・パラメータであり、オブジェクトのアクティブ化ポリシーの指定、およびスケルトン・ファイルと実装ファイルを生成するインタフェース数の制限に使用します。ICFファイルの使用方法は、「ステップ4: メモリー内でのオブジェクトの振る舞いの定義」で説明されています。
注意:
C++ IDLコンパイラはプラグマ接頭辞の処理を修正するように変更されています。この変更は、オブジェクトのリポジトリIDに影響を与え、_narrowなど、一部の操作に障害が発生する可能性があります。
このような障害を防ぐには、次の手順に従います。
idlコマンドなどのIDLコンパイラの詳細は、『CORBAプログラミング・リファレンス』を参照してください。
スケルトンと実装ファイルの生成
次のコマンド行は、OMG IDLファイルunivb.idlに対して、クライアント・スタブ・ファイル、スケルトン・ファイルおよび初期実装ファイルをスケルトン・ヘッダー・ファイルおよび実装ヘッダー・ファイルとともに生成します。
idl -i univb.idl
idlコマンドの詳細は、『CORBAプログラミング・リファレンス』を参照してください。Oracle Tuxedo Universityサンプル・アプリケーション用のこれらのファイルの生成の詳細は、CORBA Universityサンプル・アプリケーション・ガイドを参照してください。
注意:
tieクラスの生成
IDLコンパイラには、インタフェースのtieクラス・テンプレートの生成に使用できる-Tコマンド行オプションも用意されています。CORBAアプリケーションでのtieクラスの実装の詳細は、「デレゲーション・ベースのインタフェース実装」を参照してください。
ステップ2: 各インタフェースの操作を実装するメソッドの記述
サーバー・アプリケーション・プログラマのタスクは、アプリケーションのOMG IDLファイルで定義した各インタフェースの操作を実装するメソッドの記述です。
実装ファイルの内容は次のとおりです。
オプションで、Tobj_ServantBase::activate_object()およびTobj_ServantBase::deactivate_object()操作。
Tobj_ServantBase::activate_object()およびTobj_ServantBase::deactivate_object()操作内に、オブジェクトのアクティブ化または非アクティブ化に関連するステップを実行するコードを記述します。これには、オブジェクトの永続状態のディスクからの読取りとディスクへの書込みが含まれます。オブジェクトにこれらの操作を実装する場合は、実装ヘッダー・ファイルを編集し、これらの操作を使用する各実装に操作の定義を追加する必要もあります。
IDLコンパイラによって生成される実装ファイル
サーバー・アプリケーションの実装ファイルをすべて手動で作成することもできますが、IDLコンパイラによって、実装ファイルの記述の開始場所として使用できる実装ファイルが生成されます。IDLコンパイラによって生成される実装ファイルには、アプリケーションのインタフェースに定義されている各操作を実装するメソッドのシグネチャが格納されています。
通常は、IDLコンパイラを呼び出すコマンドで-iオプションを使用して、この実装ファイルを1回のみ生成します。アプリケーションのインタフェースを反復的に修正し、操作のシグネチャなど、それらのインタフェースの操作を変更する場合は、必要なすべての変更を実装ファイルに追加して、それらの変更を反映します。
ファクトリの実装
1-4ページの「クライアント・アプリケーションがサーバー・アプリケーションのCORBAオブジェクトをアクセスおよび操作する方法」という項で説明したように、サーバー・アプリケーションで管理されているオブジェクトをクライアント・アプリケーションが簡単に特定できるようにファクトリを作成する必要があります。ファクトリは、実装する他のCORBAオブジェクトに似ていますが、FactoryFinderオブジェクトに登録する点が異なります。ファクトリの登録は、2-10ページの「ファクトリを作成および登録するコードの記述」という項を参照してください。
ファクトリの主要機能は、TP::create_object_reference()操作を呼び出すことでオブジェクト参照を作成することです。TP::create_object_reference()操作には次の入力パラメータが必要です。
たとえば、Basic Universityサンプル・アプリケーションでは、RegistrarFactoryインタフェースは次の1つの操作のみ指定します。
University::Registrar_ptr RegistrarFactory_i::find_registrar()
RegistrarFactoryオブジェクトに対するfind_registrar()操作には、Registrarオブジェクトへの参照を作成するためのTP::create_object_reference()操作への次の呼出しが含まれます。
CORBA::Object_var v_reg_oref =
TP::create_object_reference(
University::_tc_Registrar->id(),
object_id,
CORBA::NVlist::_nil()
);
前のコード例で、次の点に注意してください。
次のパラメータは、Registrarオブジェクトのインタフェース・リポジトリIDをタイプ・コードから抽出して指定します。
University::_tc_Registrar->id()
次のパラメータはルーティング基準が使用されないことを指定し、その結果として、Registrarオブジェクトに対して作成されたオブジェクト参照は、そのオブジェクト参照を作成したRegistrarFactoryオブジェクトと同じグループにルーティングされます。
CORBA::NVlist::_nil()
オブジェクト参照がルーティングされるグループに影響するルーティング基準の指定については、第8章「Oracle TuxedoのCORBAサーバー・アプリケーションのスケーリング」を参照してください。
ステップ3:サーバー・オブジェクトの作成
サーバー・オブジェクトの実装はその他の言語オブジェクトの実装とは異なります。サーバー・オブジェクトのヘッダー・クラスがすでに作成されており、サーバー・オブジェクト・クラスがすでにインスタンス化されています。サーバー・オブジェクトの作成では、事前パッケージ済サーバー・オブジェクト・クラスで特定の一連のメソッドを実装します。実装するメソッドについては、この項で説明します。
サーバー・オブジェクトを作成するには、一般的なテキスト・エディタを使用して新規ファイルを作成し、表2-3に示す操作を実装します。
 
サーバー・アプリケーションには、サーバー・オブジェクトのインスタンスが1つのみあります。サーバー・アプリケーションで複数のCORBAオブジェクト実装を管理している場合、記述するServer::initialize()Server::create_servant()およびServer::release()操作には、これらすべての実装に適用するコードを含める必要があります。
これらのタスク用に記述するコードは、TPフレームワークと対話します。以降の項では、各サーバー・オブジェクト操作に必要なコードについて説明し、Basic Universityサンプル・アプリケーションのサンプル・コードを示します。
サーバー・アプリケーションの初期化
サーバー・オブジェクトで最初に実装する操作は、サーバー・アプリケーションを初期化する操作です。この操作は、Oracle Tuxedoシステムでサーバー・アプリケーションが起動すると呼び出されます。TPフレームワークは、サーバー・アプリケーションの起動シーケンス中にサーバー・オブジェクトの次の操作を呼び出します。
CORBA::Boolean Server::initialize(int argc, char** argv)
Oracle TuxedoドメインのUBBCONFIGファイルのSERVERSセクションで特定のサーバー・アプリケーションのCLOPTパラメータに指定したコマンド行オプションは、Server::initialize()操作にargcおよびargvとして渡されます。サーバー・アプリケーションへの引数の受渡しの詳細は、Oracle Tuxedoアプリケーション実行時の管理を参照してください。サーバー・アプリケーションへの引数の受渡しの例は、CORBA Universityサンプル・アプリケーション・ガイドを参照してください。
Server::initialize()操作に、次の処理を行うコードを含めます(該当する場合)。
ファクトリを作成および登録するコードの記述
クライアント・アプリケーションで簡単に特定できるファクトリをサーバー・アプリケーションで管理する場合は、そのファクトリをFactoryFinderオブジェクトに登録するコードを作成する必要があります(通常、このコードはサーバー・アプリケーション初期化プロセスの最後のステップとして呼び出されます)。
サーバー・アプリケーションで管理されるファクトリを登録するコードを記述するには、次の手順に従います。
1.
このステップでは、2-7ページの「ファクトリの実装」という項の説明に従ってオブジェクト参照を作成します。このステップでは、TP::create_object_reference()操作への呼出しを含め、ファクトリのOMG IDLインタフェースのインタフェース・リポジトリIDを指定します。次の例では、s_v_fact_ref変数で表されるRegistrarFactoryファクトリへのオブジェクト参照を作成します。
University::RegistrarFactory s_v_fact_ref =
TP::create_object_reference(
University::_tc_RegistrarFactory->id(),
object_id,
CORBA::NVList::_nil()
);
2.
このステップでは、サーバー・アプリケーションで管理される各ファクトリについて次の操作を呼び出します。
TP::register_factory (CORBA::Object_ptr factory_or,
const char* factory_id);
TP::register_factory()操作は、サーバー・アプリケーションのファクトリをFactoryFinderオブジェクトに登録します。この操作には、次の入力パラメータが必要です。
次の例は、RegistrarFactoryファクトリをOracle Tuxedoドメインに登録します。
TP::register_factory(s_v_fact_ref.in(),
University::_tc_RegistrarFactory->id());
パラメータUniversity::_tc_RegistrarFactory->id()に注意してください。これは、TP::create_object_reference()操作で指定したパラメータと同じです。このパラメータは、オブジェクトのOMG IDLインタフェースのインタフェース・リポジトリIDをそのタイプコードから抽出します。
サーバントの作成
サーバー・アプリケーションの初期化プロセスの完了後に、サーバー・アプリケーションはクライアント・リクエストの処理を開始する準備ができます。メモリー内に使用可能なサーバントがないCORBAオブジェクトに対する操作のリクエストが到着した場合、TPフレームワークはサーバー・オブジェクトで次の操作を呼び出します。
Tobj_Servant Server::create_servant(const char* interfaceName)
Server::create_servant()操作には、クライアント・リクエストに必要なオブジェクトのサーバントをインスタンス化するコードが含まれます。たとえば、C++では、このコードにオブジェクトのインタフェース・クラスに対するnew文が含まれます。
Server::create_servant()操作は、サーバントをOIDに関連付けません。サーバントとOIDの関連付けは、TPフレームワークがサーバントに対してオブジェクトのインスタンスを完了するTobj_ServantBase::activate_object()操作を呼び出すときに行われます。(OIDをオブジェクトのコンストラクタ内のオブジェクトに関連付けることはできません。)同様に、サーバントとOIDの関連付けの解除は、TPフレームワークがサーバントに対してdeactivate_object()操作を呼び出すときに行われます。
Oracle Tuxedoシステムでのサーバントのこの動作により、オブジェクトが非アクティブ化された後で、TPフレームワークはサーバントを別のオブジェクト・インスタンス化で使用可能にすることができます。このため、オブジェクトのTobj_ServantBase::deactivate_object()操作の呼出しによって、そのオブジェクトのデストラクタが呼び出されるとは仮定しないでください。サーバー・アプリケーションでサーバント・プール機能を使用した場合、オブジェクトのTobj_ServantBase::deactivate_object()操作にTP::application_responsibility()操作を実装して、後で再利用できるようにサーバントのポインタをサーバント・プールに渡すことができます。サーバント・プールについては、「サーバント・プール」を参照してください。
Server::create_servant()操作には、単一の入力引数が必要です。引数では、サーバントを作成しているオブジェクトのOMG IDLインタフェースのインタフェース・リポジトリIDを含む文字列を指定します。
この操作のコードでは、サーバー・アプリケーションで管理されるオブジェクトのOMG IDLインタフェースのインタフェース・リポジトリIDを指定します。実行時に、Server::create_servant()操作は、リクエストで指定されたオブジェクトに必要なサーバントを返します。
次のコードは、Basic Universityサンプル・アプリケーションからUniversityサーバー・アプリケーションのServer::create_servant()操作を実装します。
Tobj_Servant Server::create_servant(const char* intf_repos_id)
{
if (!strcmp(intf_repos_id, University::_tc_RegistrarFactory->id())) {
return new RegistrarFactory_i();
}
if (!strcmp(intf_repos_id, University::_tc_Registrar->id())) {
return new Registrar_i();
}
if (!strcmp(intf_repos_id, University::_tc_CourseSynopsisEnumerator->id())) {
return new CourseSynopsisEnumerator_i();
}
return 0; // unknown interface
}
サーバー・アプリケーションのリリース
Oracle Tuxedoシステム管理者がtmshutdownコマンドを入力すると、TPフレームワークはOracle Tuxedoドメインで実行している各サーバー・アプリケーションのサーバー・オブジェクトで次の操作を呼び出します。
void Server::release()
Server::release()操作内で、サーバー・アプリケーションに固有の次のようなアプリケーション固有クリーンアップ・タスクを実行できます。
停止のリクエストを受信すると、サーバー・アプリケーションは他のリモート・オブジェクトからのリクエストを受信できなくなります。このことはサーバー・アプリケーションの停止順序に影響を与えますが、これは管理タスクです。たとえば、サーバー・プロセスの停止は、2番目のサーバー・プロセスのServer::release()操作に最初のサーバー・プロセスの呼出しが含まれている場合は行わないでください。
サーバー停止時に、サーバー・アプリケーションの各ファクトリを登録解除するために次の呼出しを含める必要があります。
TP::unregister_factory (CORBA::Object_ptr factory_or,
const char* factory_id)
TP::unregister_factory()操作の呼出しは、Server::release()実装の最初のアクションとして行う必要があります。TP::unregister_factory()操作では、サーバー・アプリケーションのファクトリの登録が解除されます。この操作では、次の入力引数が必要です。
次の例は、Basicサンプル・アプリケーションで使用されているRegistrarFactoryファクトリを登録解除します。
TP::unregister_factory(s_v_fact_ref.in(), UnivB::_tc_RegistrarFactory->id());
前のサンプル・コードのグローバル変数s_v_fact_refの使用方法に注意してください。この変数は、RegistrarFactoryオブジェクトを登録したServer::initialize()操作で設定され、ここで再度使用されています。
パラメータUnivB::_tc_RegistrarFactory->id()にも注意してください。これは、ファクトリの登録に使用されるインタフェース名とも同じです。
ステップ4:メモリー内でのオブジェクトの振る舞いの定義
「オブジェクト状態の管理」で説明しているように、オブジェクト・アクティブ化ポリシーとトランザクション・ポリシーの割当てによって、またオプションでアプリケーションで制御される非アクティブ化機能を使用して、オブジェクトが非アクティブ化される原因となるイベントを決定します。
ICFファイルにオブジェクトのアクティブ化ポリシーとトランザクション・ポリシーを指定し、TP::deactivateEnable()操作を介してアプリケーションで制御される非アクティブ化を実装します。この項では、Basic Universityサンプル・アプリケーションを例として使用して、両方のメカニズムの実装方法を説明します。
以降の項で説明する内容は次のとおりです。
ICFでオブジェクトのアクティブ化ポリシーとトランザクション・ポリシーを指定する方法
Oracle Tuxedoソフトウェアは、1-11ページの「オブジェクトのアクティブ化ポリシー」で説明している表2-4のアクティブ化ポリシーをサポートします。
 
オブジェクトによる自身のTP::deactivateEnable()操作の呼出し。
Oracle Tuxedoソフトウェアは、第6章「トランザクションのCORBAサーバー・アプリケーションへの統合」で説明している次のトランザクション・ポリシーもサポートします。
 
これらのポリシーをアプリケーションのオブジェクトに割り当てるには、次の手順に従います。
1.
次の例のようにアプリケーションのOMG IDLファイルを入力として指定してgenicfコマンドを入力することで、ICFファイルを生成します。
# genicf university.idl
前のコマンドはファイルuniversity.icfを生成します。
2.
module POA_UniversityB
{
implementation CourseSynopsisEnumerator_i
{
activation_policy ( method );
transaction_policy ( optional );
implements ( UniversityB::CourseSynopsisEnumerator );
};
};
module POA_UniversityB
{
implementation Registrar_i
{
activation_policy ( method );
transaction_policy ( optional );
implements ( UniversityB::Registrar );
};
};
module POA_UniversityB
{
implementation RegistrarFactory_i
{
activation_policy ( method );
transaction_policy ( optional );
implements ( UniversityB::RegistrarFactory );
};
};
3.
implementation RegistrarFactory_i
{
activation_policy ( method );
transaction_policy ( optional );
implements ( UniversityB::RegistrarFactory );
};
4.
ステップ5:サーバー・アプリケーションのコンパイルとリンク
サーバー・オブジェクトとオブジェクト実装のコードの記述が完了したら、サーバー・アプリケーションをコンパイルおよびリンクする必要があります。
注意:
CORBAサーバー・アプリケーションをコンパイルとリンクするには、buildobjserverコマンドを使用する必要があります。
buildobjserverコマンドの形式は次のとおりです。
buildobjserver [-o servername] [options]
buildobjserverコマンド構文の意味は次のとおりです。
-o servernameは、このコマンドで生成されるサーバー・アプリケーションの名前を表します。
optionsは、buildobjserverコマンドのコマンド行オプションを表します。
Universityサンプル・アプリケーションのコンパイルとリンクの詳細は、『CORBA Universityサンプル・アプリケーション・ガイド』を参照してください。buildobjserverコマンドの詳細情報は、Oracle Tuxedoコマンド・リファレンスを参照してください。
マルチスレッドCORBAサーバー・アプリケーションの設計とビルドには特別な考慮事項があります。4-13ページの「buildobjserverコマンドの使い方」を参照してください。
注意:
Oracle TuxedoソフトウェアをIBM AIX 4.3.3システムで実行している場合は、-brtlコンパイラ・オプションを使用してCORBAアプリケーションを再コンパイルする必要があります。
ステップ6:サーバー・アプリケーションのデプロイ
自分またはシステム管理者が、この項で説明されている手順に従ってCORBAサーバー・アプリケーションをデプロイします。Universityサンプル・アプリケーションのビルドとデプロイの詳細は、『CORBA Universityサンプル・アプリケーション・ガイド』を参照してください。
サーバー・アプリケーションをデプロイするには、次の手順に従います。
1.
2.
UBBCONFIGファイルとも呼ばれるアプリケーションの構成ファイルを一般的なテキスト・エディタで作成します。
3.
UBBCONFIGファイルのTUXCONFIGエントリと完全に一致する必要のあるTUXCONFIG。この変数は、アプリケーションのUBBCONFIGファイルの場所またはパスを表します。
アプリケーションの実行可能ファイルが存在するディレクトリを表すAPPDIR
4.
Oracle Tuxedoドメインで実行されているかOracle Tuxedoドメインに接続されているすべてのマシンにTUXDIR環境変数を設定します。この環境変数は、Oracle Tuxedoソフトウェアがインストールされている場所を指します。
5.
次のコマンドを入力してTUXCONFIGファイルを作成します。
tmloadcf -y application-ubbconfig-file
コマンド行引数application-ubbconfig-fileは、アプリケーションのUBBCONFIGファイルの名前を表します。このコマンドを実行するには古いTUXCONFIGファイルを削除することが必要な場合があります。
6.
tmboot -y
UBBCONFIGファイルを再ロードせずにサーバー・アプリケーションを再起動できます。
Universityサンプル・アプリケーションの構成の詳細は、『CORBA Universityサンプル・アプリケーション・ガイド』を参照してください。CORBAアプリケーションのUBBCONFIGファイルの作成の詳細は、Oracle Tuxedoアプリケーションの設定を参照してください。
開発とデバッグのヒント
このトピックには次の項が含まれます:
Tobj_ServantBase::deactivate_object()操作での状態処理に関する注意
CORBA例外とユーザー・ログの使い方
このトピックには次の項が含まれます:
例外のクライアント・アプリケーション・ビュー
クライアント・アプリケーションがCORBAオブジェクトに対する操作を呼び出すと、呼出しの結果として例外が返されることがあります。次の有効な例外のみをクライアント・アプリケーションに返すことができます。
Oracle Tuxedoシステムは、「例外のサーバー・アプリケーション・ビュー」で説明するように、これらのCORBA定義制限に違反しないように動作します。
クライアント・アプリケーションに公開されている一連の例外は制限されているため、クライアント・アプリケーションは原因があいまいな例外を捕捉することがあります。可能な場合、Oracle Tuxedoシステムは、このような例外をユーザー・ログの説明のメッセージで補足します。これは、エラー状態の検出およびデバッグに役立ちます。これらのケースについては、次の項で説明します。
例外のサーバー・アプリケーション・ビュー
このトピックには次の項が含まれます:
Oracle Tuxedoシステムによって生成され、アプリケーション・コードによって捕捉される例外
Oracle Tuxedoシステムは、TPオブジェクトに対する操作が呼び出されたときにアプリケーションに次のタイプの例外を戻すことがあります。
TobjS_c.hファイルで定義されたCORBA UserExceptions。このファイルで定義されている例外のOMG IDLは次のとおりです。
interface TobjS {
exception AlreadyRegistered { };
exception ActivateObjectFailed { string reason; };
exception ApplicationProblem { };
exception CannotProceed { };
exception CreateServantFailed { string reason; };
exception DeactivateObjectFailed { string reason; };
exception IllegalInterface { };
exception IllegalOperation { };
exception InitializeFailed { string reason; };
exception InvalidDomain { };
exception InvalidInterface { };
exception InvalidName { };
exception InvalidObject { };
exception InvalidObjectId { };
exception InvalidServant { };
exception NilObject { string reason; };
exception NoSuchElement { };
exception NotFound { };
exception OrbProblem { };
exception OutOfMemory { };
exception OverFlow { };
exception RegistrarNotAvailable { };
exception ReleaseFailed { string reason; };
exception TpfProblem { };
exception UnknownInterface { };
}
CORBAオブジェクトの操作の呼出し中にアプリケーション・コードによって生成された例外をOracle Tuxedoシステムが処理する方法
サーバー・アプリケーションは、クライアント呼出しの処理中に次の場所で例外を生成することがあります。
Server::create_servantTobj_ServantBase::activate_object()およびTobj_ServantBase::deactivate_object()コールバック・メソッド内。
サーバー・アプリケーションは次のいずれかのタイプの例外を生成することがあります。
TobjS_c.hファイルで定義されたCORBAユーザー定義例外。次の例外は、Oracle Tuxedoシステムがトラブルシューティングに役立つユーザー・ログにメッセージを送信できるようにサーバー・アプリケーションで使用することを目的としています。
interface TobjS {
exception ActivateObjectFailed { string reason; };
exception CreateServantFailed { string reason; };
exception DeactivateObjectFailed { string reason; };
exception InitializeFailed { string reason; };
exception ReleaseFailed { string reason; };
}
サーバー・アプリケーション・コードで生成され、サーバー・アプリケーションで捕捉されないすべての例外は、Oracle Tuxedoシステムによって捕捉されます。これらの例外が捕捉されると、次のいずれかが行われます。
次の各項では、CORBAオブジェクトに対するクライアント呼出し中にサーバー・アプリケーションが生成した例外をOracle Tuxedoシステムが処理する方法を示します。
Server::create_servant()操作で発生する例外
Server::create_servant()操作で例外が発生した場合、次の処理が行われます。
CORBA::OBJECT_NOT_EXIST例外がクライアント・アプリケーションに返されます。
発生した例外がTobjS::CreateServantFailedの場合は、メッセージがユーザー・ログに送信されます。例外のコンストラクタで理由の文字列が提供されている場合は、理由文字列もメッセージの一部として書き込まれます。
Tobj_ServantBase::activate_object()またはTobj_ServantBase::deactivate_object()操作はどちらも呼び出されません。クライアントによってリクエストされた操作は呼び出されません。
Tobj_ServantBase::activate_object()操作で発生する例外
Tobj_ServantBase::activate_object()操作で例外が発生した場合、次の処理が行われます。
CORBA::OBJECT_NOT_EXIST例外がクライアント・アプリケーションに返されます。
発生した例外がTobjS::ActivateObjectFailedの場合は、メッセージがユーザー・ログに送信されます。例外のコンストラクタで理由の文字列が提供されている場合は、理由文字列もメッセージの一部として書き込まれます。
クライアントによってリクエストされた操作とTobj_ServantBase::deactivate_object()操作はどちらも呼び出されません。
操作実装で発生した例外
Oracle Tuxedoシステムは、操作実装がCORBAシステム例外、またはクライアント・アプリケーションで認識されているOMG IDLで定義されたユーザー定義例外をスローすることを要求します。操作実装によってこれらのタイプの例外がスローされると、Oracle Tuxedoシステムは、次の状態が存在する場合を除き、これらの例外をクライアント・アプリケーションに返します。
オブジェクトにalwaysトランザクション・ポリシーがあり、オブジェクトが呼び出されたときにOracle Tuxedoシステムがトランザクションを自動的に開始した場合。この場合、トランザクションはOracle Tuxedoシステムによって自動的にロールバックされます。クライアント・アプリケーションはトランザクションを認識しないため、Oracle Tuxedoシステムは、クライアントがトランザクションを開始した場合に生成されるCORBA:: TRANSACTION_ROLLEDBACK例外ではなく、CORBA::OBJ_ADAPTER CORBAシステム例外を生成します。
例外がファイルTobjS_c.hで定義されている場合。この場合、例外はCORBA::BAD_OPERATION例外に変換され、クライアント・アプリケーションに戻されます。また、次のメッセージがユーザー・ログに送信されます。
「警告: アプリケーションがTobjS例外を捕捉しませんでした。TPフレームワークがCORBA::BAD_OPERATIONをスローしています。」
例外がTobjS::IllegalOperationの場合は、次の補足メッセージが書き込まれ、アプリケーションのコーディング・エラーの可能性が開発者に警告されます。
「警告: アプリケーションがTP::deactivateEnable()を不正に呼出し、TobjS例外を捕捉しませんでした。」
この状況は、transactionアクティブ化ポリシーを持つオブジェクトの内部でTP::deactivateEnable()操作が呼び出された場合に発生することがあります。(アプリケーションで制御される非アクティブ化は、トランザクション・バウンド・オブジェクトに対してサポートされません。)
Oracle Tuxedoシステムがクライアント呼出しに続いて内部システム例外を生成した場合。この場合は、CORBA::INTERNAL例外がクライアント・アプリケーションに返されます。これは通常、オブジェクトがアクティブなプロセスでの重大なシステムの問題を示しています。
CORBA標準で定義されているように、クライアントに返信された応答には、操作実装からの結果値、または操作実装でスローされた例外が含まれている場合がありますが、その両方が含まれることはありません。最初の場合(応答ステータス値がNO_EXCEPTIONの場合)では、応答に操作の戻り値とinoutまたはout引数値が含まれます。それ以外(応答ステータス値がUSER_EXCEPTIONまたはSYSTEM_EXCEPTION)の場合は、すべての応答に例外のエンコーディングが含まれます。
Tobj_ServantBase::deactivate_object()操作で発生する例外
Tobj_ServantBase::deactivate_object()操作で例外が発生した場合、次の処理が行われます。
発生した例外がTobjS::DectivateObjectFailedの場合は、メッセージがユーザー・ログに送信されます。例外のコンストラクタで理由の文字列が提供されている場合は、理由文字列もメッセージの一部として書き込まれます。
TobjS::DeactivateObjectFailed例外以外の例外については、Oracle Tuxedoシステムで捕捉された例外のタイプを示すメッセージがユーザー・ログに送信されます。
オブジェクト・インスタンスを渡すときに発生するCORBAマーシャリング例外
ORBはオブジェクト・インスタンスをオブジェクト参照としてマーシャリングできません。たとえば、次のコードでファクトリ参照を受け渡すと、Oracle TuxedoシステムでCORBAマーシャリング例外が発生します。
connection::setFactory(this);
オブジェクト・インスタンスを受け渡すには、次の例のように、プロキシ・オブジェクト参照を作成して、そのプロキシをかわりに受け渡します。
CORBA::Object myRef = TP::get_object_reference();
ResultSetFactory factoryRef = ResultSetFactoryHelper::_narrow(myRef);
connection::setFactoryRef(factoryRef);
コールバック・メソッドのエラー状態の検出
Oracle Tuxedoシステムには、アプリケーション・コードの次のコールバック・メソッドのいずれかでエラーが発生した場合にTPフレームワークがユーザー・ログに書き込むメッセージ文字列を指定できる事前定義済例外のセットが用意されています。
これらの例外を有用なデバッグ支援として使用し、例外が発生している理由に関する明白な情報を送信できます。TPフレームワークは、これらのメッセージをユーザー・ログにのみ書き込みます。これらのメッセージは、クライアント・アプリケーションには返されません。
これらのメッセージは、表2-5に示す、オプションの理由文字列を持つ例外で指定します。
 
表2-5 例外
メッセージ文字列をユーザー・ログに送信するには、次の例のように例外に文字列を指定します。
throw CreateServantFailed("Unknown interface");
これらの例外をスローする場合は、理由文字列パラメータが必要です。これらのいずれかの例外で文字列を指定しない場合は、次の例のように二重引用符文字を使用する必要があります。
throw ActivateObjectFailed("");
OMG IDLインタフェースのバージョンと修正に関する一般的な注意事項
サーバー・オブジェクトのServer::create_servant()操作の実装は、インタフェースIDに基づいてオブジェクトをインスタンス化します。このインタフェースIDは、ファクトリがTP::create_object_reference()操作を呼び出すときにファクトリに提供されたインタフェースIDと同じであることが重要です。インタフェースIDが一致しない場合、Server::create_servant()操作は通常、例外を生成するか、NULLサーバントを戻します。Oracle Tuxedoシステムは、クライアント・アプリケーションにCORBA::OBJECT_NOT_EXIST例外を戻します。Oracle Tuxedoシステムは、TP::create_object_reference()操作でインタフェースIDの検証を実行しません。
開発時に様々なバージョンのインタフェースを開発したり、IDLファイルを何度も変更すると、この状態が発生する可能性があります。通常はOMG IDLでインタフェースIDの文字列定数を指定し、これらをファクトリとServer::create_servant()操作で使用しますが、オブジェクト実装とファクトリが異なる実行可能ファイルにある場合は不一致が発生することがあります。この潜在的な問題は診断が困難です。
この潜在的な問題を回避するために、開発時に次の防御的なプログラミング戦略を検討する必要があります。このコードは、ソフトウェアの本番バージョンでは許容できないパフォーマンスの低下をもたらす可能性があるため、アプリケーションのデバッグ・バージョンにのみ含める必要があります。
ファクトリがTP::create_object_reference()操作を呼び出す直前に、インタフェース・リポジトリをチェックして必要なインタフェースが存在するかどうかを確認するコードを含めます。すべてのアプリケーションOMG IDLが最新であり、インタフェース・リポジトリにロードされていることを確認してください。このチェックでインタフェースIDが見つからない場合は、不一致であることを想定できます。
ファクトリでのTP::create_object_reference()操作の呼出しに続いて、オブジェクトを"ping"するコードを含めます。つまり、コードはオブジェクトに対して任意の操作(通常は何も行わない操作)を呼び出します。この呼出しでCORBA::OBJECT_NOT_EXIST例外が発生する場合は、インタフェースIDの不一致が存在します。オブジェクトの"ping"によってオブジェクトがアクティブになり、アクティブ化に関連するオーバーヘッドが発生することに注意してください。
Tobj_ServantBase::deactivate_object()での状態処理に関する注意
Tobj_ServantBase::deactivate_object()操作は、オブジェクトのアクティブ化境界に達したときに呼び出されます。オプションで、この操作の実装で永続状態をディスクに書き込むことができます。この操作で発生した例外はクライアント・アプリケーションに戻されないことに注意してください。クライアント・アプリケーションは、オブジェクトがトランザクションに関与していないかぎり、この操作で発生したエラー条件を認識しません。したがって、この操作を介した状態の書込みに成功したかどうかをクライアント・アプリケーションが知る必要がある場合は、トランザクションを使用することをお薦めします。
状態の書込みにTobj_ServantBase::deactivate_object()操作を使用することに決め、クライアント・アプリケーションが書込み操作の結果を知る必要がある場合は、次の処理を実行することをお薦めします。
オブジェクト状態に影響する各操作がトランザクション内で呼び出され、非アクティブ化がトランザクション境界内で行われることを確認します。これは、methodまたはtransactionアクティブ化ポリシーを使用して行うことができ、TP::deactivateEnable()操作がトランザクション境界内で呼び出される場合はprocessアクティブ化ポリシーで行うこともできます。
オブジェクト状態の書込み中にエラーが発生する場合は、COSTransactions::Current::rollback_only()操作を呼び出して、トランザクションがロールバックされるようにします。これにより、クライアント・アプリケーションが次のいずれかの例外を受け取ります。
トランザクションが使用されていない場合は、Tobj_ServantBase::deactivate_object()操作を使用するかわりに、オブジェクトに対する個々の操作のスコープ内でオブジェクト状態を書き込むことをお薦めします。これにより、エラーが発生した場合に、操作はクライアント・アプリケーションに戻される例外を生成できます。
サーバント・プール
「サーバント・プールとステートレス・オブジェクト」で説明したように、サーバント・プールはメソッド・バウンド・オブジェクトまたはトランザクション・バウンド・オブジェクトのオブジェクト・インスタンス化のコストを削減する手段を提供します。
サーバント・プールの機能
通常、オブジェクトの非アクティブ化中(つまり、TPフレームワークがTobj_ServantBase::deactivate_object()操作を呼び出すとき)、TPフレームワークはオブジェクトのサーバントを削除します。ただし、サーバント・プールが使用されるときは、TPフレームワークはオブジェクトの非アクティブ化時にサーバントを削除しません。かわりに、サーバー・アプリケーションはプール内でサーバントへのポインタを維持します。当該プールでサーバントによって満たされる後続のクライアント・リクエストが受信されると、サーバー・アプリケーションはサーバントを再使用して新規オブジェクトIDを割り当てます。サーバントがプールから再使用されるとき、TPフレームワークは新規サーバントを作成しません。
サーバント・プールの実装方法
次の操作を実行することで、サーバント・プールを実装します。
1.
サーバー・オブジェクトに対するServer::initialize()操作で、サーバント・プールを設定するコードを記述します。プールは1つ以上のサーバントへのポインタのセットから構成され、プールのコードはプールに維持される特定のクラスのサーバント数を指定します。
2.
プールされたサーバントのTobj_ServantBase::deactive_object()操作で、TP::application_responsibility()操作を実装します。TP::application_responsibility()操作の実装で、TPフレームワークによってTobj_ServantBase::deactivate_object()操作が呼び出されるときにサーバントへのポインタをサーバント・プールに配置するコードを提供します。
3.
サーバー・オブジェクトのServer::create_servant()操作の実装で、クライアント・リクエストの到着時に次の処理を実行するコードを記述します。
a.
b.
サーバントが存在しない場合は、サーバントを作成し、それに対してTobj_ServantBase::activate_object()操作を呼び出します。
c.
サーバントが存在する場合は、それに対してTobj_ServantBase::activate_object()操作を呼び出し、クライアント・リクエストに含まれているオブジェクトIDを割り当てます。
注意:
TP::application_responsibility()操作のサポートは、このリリースで変更されました。詳細は、『CORBAプログラミング・リファレンス』を参照してください。
デレゲーション・ベースのインタフェース実装
Oracle Tuxedo CORBAアプリケーションでオブジェクトを実装するには、継承とデレゲーションの2つの主要な方法があります。オブジェクトがPOAスケルトン・クラスを継承しており、したがってCORBAオブジェクトである場合、そのオブジェクトは継承によって実装されているとみなされます。
一方、POAスケルトン・クラスからの継承が難しいか実際的ではないCORBAアプリケーションでは、C++オブジェクトを使用する場合もあります。たとえば、POAスケルトン・クラスを継承するために大幅な書換えが必要なC++オブジェクトがある場合です。この非CORBAオブジェクトをCORBAアプリケーションに格納するには、オブジェクトのtieクラスを作成します。このtieクラスはPOAスケルトン・クラスから継承し、tieクラスにはこれらの操作の実装用のレガシー・クラスに委任する1つ以上の操作が含まれます。レガシー・クラスは、デレゲーションによってCORBAアプリケーションで実装されます。
Oracle Tuxedoシステムのtieクラスについて
デレゲーション・ベースのインタフェース実装を作成するには、IDLコンパイラの-Tコマンド行オプションを使用して、OMG IDLファイルで定義されたインタフェースごとにtieクラス・テンプレートを生成します。
CORBAアプリケーションでのtieクラスの使用は、サーバー・オブジェクトでのServer::create_servant()操作の実装方法にも影響します。次の各項では、Oracle Tuxedo製品でのtieクラスの使用方法を詳細に説明し、これらのクラスをインスタンス化するためのServer::create_servant()操作の実装方法も説明します。
Oracle Tuxedo CORBAでは、tieクラスはサーバントであるため、基本的にレガシー・クラスのラッパー・オブジェクトとして機能します。
表2-1に、レガシー・オブジェクトのラッパーとして機能するインタフェースAccountの継承特性を示します。レガシー・オブジェクトには、操作op1の実装が含まれます。tieクラスはop1をレガシー・クラスに委任します。
図2-1 インタフェースAccountの継承特性
tieクラスはクライアント・アプリケーションに対して透過的です。クライアント・アプリケーションでは、tieクラスはクライアント・アプリケーションが呼び出したオブジェクトの完全な実装であるように見えます。tieクラスは、すべての操作を指定したレガシー・クラスに委任します。また、tieクラスには次のものが含まれます。
tieクラスを使用する条件
tieクラスはOracle Tuxedo CORBAに固有のものではなく、CORBAアプリケーションでデレゲーションを実装する唯一の方法ではありません。ただし、tieクラスに対するOracle Tuxedo CORBAの便利な機能により、これらのtieクラスの基本的なコンストラクタ、デストラクタおよびハウスキーピング操作に対して行う必要のあるコーディングの量を大幅に減らすことができます。
tieクラスの使用は、次のいずれかの状況でお薦めします。
tieクラスは、次の場合には推奨されません
CORBAアプリケーションにtieクラスを作成する方法
Oracle Tuxedoドメインのアプリケーションでtieクラスを作成するには、次の手順に従います。
1.
2.
-Tオプションを使用してOMG IDLファイルをコンパイルします。
IDLコンパイラは、スケルトンの名前に文字列_tieを追加したC++テンプレート・クラスを生成します。IDLコンパイラは、このテンプレート・クラスをスケルトン・ヘッダー・ファイルに追加します。
IDLコンパイラは、tieクラスの実装ファイルを生成しません。このファイルは次のステップで説明するように手動で作成する必要があります。
3.
4.
サーバー・オブジェクトのServer::create_servant()操作で、レガシー・オブジェクトをインスタンス化するコードを記述します。
次の例では、tieクラスPOA_Account_tieのサーバントが作成され、レガシー・クラスLegacyAccountがインスタンス化されます。
Account * Account_ptr = new LegacyAccount();
AccountFactoryServant = new POA_Account_tie<LegacyAccount> (Account_ptr)
注意:
UNIX用のCompaq C++ Tru64コンパイラでtieクラスをコンパイルする場合は、buildobjserverコマンドで使用されるCFLAGSまたはCPPFLAGS環境変数の定義に-noimplicit_includeオプションを含める必要があります。このオプションは、多重定義シンボル・エラーを回避するために必要なサーバー・スケルトン・ヘッダー・ファイル(_s.h)がインクルードされるすべての場所にC++コンパイラがサーバー・スケルトン定義ファイル(_s.cpp)を自動的にインクルードすることを防ぎます。Tru64 C++でのtieクラスなどのクラス・テンプレートとの使用の詳細は、Compaqのマニュアルを参照してください。
 

Copyright ©1994, 2017,Oracle and/or its affiliates. All rights reserved