目次 前 次 PDF


会話型クライアントおよびサーバーのコーディング

会話型クライアントおよびサーバーのコーディング
このトピックには次の項が含まれます:
会話型通信の概要
会話型通信はOracle Tuxedoシステムのメッセージ交換のパラダイムで、人の会話に似た通信がATMIクライアントおよびサーバー間で実装されています。この通信方法では、クライアント(イニシエータ)とサーバー(サブオーディネート)間で仮想接続が行われて、双方で会話の状態に関する情報が保持されます。この接続は、接続を終了するイベントが発生するまで継続します。
会話型通信では、クライアントとサーバー間に半二重接続が確立されます。半二重接続では、メッセージが1方向だけに送信されます。接続に関する制御は、イニシエータからサブオーディネートへ、またはその逆に移ります。制御を持つプロセスがメッセージを送信でき、持たないプロセスは受信しかできません。
以下に銀行業務のオンライン・アプリケーションを例に、Oracle Tuxedo ATMIアプリケーションで行われる会話型通信について説明します。この例では、銀行の顧客が過去2か月間の当座預金の明細書をリクエストしています。
図7-1 銀行業務オンライン・アプリケーションでの会話型通信の例
1.
顧客が過去2か月間の当座預金口座の明細書をリクエストします。
2.
口座レコード管理システムは、当座預金口座の最初の月の明細書を送信し、次に、次の月の明細書を送信するかどうかをMoreプロンプトで確認して応答します。
3.
顧客はMoreプロンプトを選択して、次の月の明細書をリクエストします。
注意:
口座レコード管理システムでは、状態情報を保持して、顧客がMoreプロンプトを選択した場合にどの明細書を送るのか認識できるようにする必要があります。
4.
口座レコード管理システムは、次の月の明細書を送信します。
リクエスト/レスポンス型通信の場合と同じように、Oracle Tuxedoシステムでは型付きレコードを使用してデータが渡されます。アプリケーションがレコード・タイプを認識できることが必要です。レコード・タイプの詳細は、3-1ページの「型付きレコードの概要」を参照してください。
会話型のクライアントおよびサーバーには、次の特徴があります。
会話型のクライアントとサーバー間の論理接続は、接続が終了するまで継続します。
会話型のクライアントとサーバー間の接続で転送できるメッセージの数には制限はありません。
クライアントとサーバーとの会話では、データの送受信にTPSENDおよびTPRECVルーチンが使用されます。
会話型通信は、次の点でリクエスト/レスポンス型通信と異なります。
会話型クライアントは、サービスをリクエストするときにTPCALLまたはTPACALLではなく、TPCONNECTを使用します。
会話型クライアントは、会話型サーバーにサービス・リクエストを送信します。
会話型サービスを定義するために、構成ファイルに会話型サーバーの一部が予約されています。
会話型サーバーは、TPFORWARを使用して呼出しを行うことはできません。
アプリケーションへの参加
会話型クライアントは、サービスへの接続を確立する前に、TPINITIALIZEを呼び出してアプリケーションに参加する必要があります。詳細は、『C言語を使用したOracle Tuxedo ATMIアプリケーションのプログラミング』クライアントのコーディングに関する項を参照してください。
接続の確立
TPCONNECT(3cbl)ルーチンは、会話を設定します。
TPCONNECTルーチンの呼出しには、次のシグネチャを使用します。
01 TPSVCDEF-REC.
COPY TPSVCDEF.
01 TPTYPE-REC.
COPY TPTYPE.
01 DATA-REC.
COPY User Data.
01 TPSTATUS-REC.
COPY TPSTATUS.
CALL "TPCONNECT" USING TPSVCDEF-REC TPTYPE-REC DATA-REC TPSTATUS-REC.
TPSVCDEF-RECレコードの詳細は「サービスの定義」TPTYPE-RECレコードの詳細は3-6ページの「型付きレコードの定義」を参照してください。
接続が確立されると同時に、DATA-RECを使用して、LEN IN TPTYPE-RECに指定されたデータ長でデータを送信できます。DATA-RECのデータのREC-TYPESUB-TYPEは、呼び出されたサービスで認識できるタイプであることが必要です。データが送信されていない場合、REC-TYPEの値はSPACESになり、DATA-RECLENは無視されます。
TPCONNECTまたは TPSVCSTARTによって接続が確立されると、Oracle Tuxedoシステムから通信ハンドル(COMM-HANDLE IN TPSVCDEF-REC)が戻されます。このCOMM-HANDLEは、特定の会話で以降に送られるメッセージを識別するために使用されます。クライアントまたは会話型サービスは、複数の会話に同時に参加できます。最大64個の会話を同時に行うことができます。
TPCONNECTの呼出しが失敗すると、対応するエラー・コードがTP-STATUSに設定されます。エラー・コードのリストについては、『Oracle Tuxedo ATMI COBOL関数リファレンス』「TPCONNECT(3cbl)」を参照してください。
次のサンプル・コードは、TPCONNECTルーチンの使用方法を示しています。
リスト7-1 会話型接続の確立
    . . .
* Prepare the record to send
  MOVE "HELLO" TO DATA-REC.
  MOVE 5 TO LEN.
  MOVE "STRING" TO REC-TYPE.
*
  SET TPBLOCK TO TRUE.
  SET TPNOTRAN TO TRUE.
  SET TPNOTIME TO TRUE.
  SET TPSIGRSTRT TO TRUE.
  SET TPSENDONLY TO TRUE.
*
  CALL "TPCONNECT" USING TPSVCDEF-REC
                   TPTYPE-REC
                   DATA-REC
                   TPSTATUS-REC.
  IF NOT TPOK
           error processing ...
  ELSE
      COMM-HANDLE is valid.
 
メッセージの送受信
Oracle Tuxedoシステムで会話型接続が確立されると、イニシエータとサブオーディネート間の通信は送信呼出しと受信呼出しを使用して行われます。接続の制御を持つプロセスはTPSEND(3cbl)ルーチンを使用してメッセージを送信し、制御がないプロセスはTPRECV(3cbl)ルーチンを使用してメッセージを受信できます。
注意:
発信元(クライアント)は、最初にTPCONNECT呼出しのTPSENDONLYまたはTPRECVONLYフラグの値を使用して、どのプロセスが制御を持っているのかを判別します。TPSENDONLYは、発信元が制御を持つことを示し、TPRECVONLYは、呼び出されたサービスに制御が渡されたことを示します。
メッセージの送信
メッセージを送信するには、TPSEND(3cbl)ルーチンを使用して次のシグネチャを呼び出します。
01 TPSVCDEF-REC.
COPY TPSVCDEF.
01 TPTYPE-REC.
COPY TPTYPE.
01 DATA-REC.
COPY User Data.
01 TPSTATUS-REC.
COPY TPSTATUS.
CALL "TPSEND" USING TPSVCDEF-REC TPTYPE-REC USER-DATA-REC TPSTATUS-REC.
TPSVCDEF-RECレコードの詳細は『C言語を使用したOracle Tuxedo ATMIアプリケーションのプログラミング』サービスの定義に関する項TPTYPE-RECレコードの詳細は3-6ページの「型付きレコードの定義」を参照してください。
TPSENDルーチンが失敗すると、対応するエラー・コードがTP-STATUSに設定されます。エラー・コードのリストについては、『Oracle Tuxedo ATMI COBOL関数リファレンス』「TPSEND(3cbl)」を参照してください。
TPSENDルーチンを呼び出すたびに、制御を渡す必要はありません。一部のアプリケーションでは、TPSENDの呼出しを認められているプロセスが、制御を他のプロセスに渡すまで、現在のタスクで必要な回数だけ呼出しを実行できます。ただし、プログラムのロジックによっては、会話が継続する間は常に1つのプロセスが接続の制御を持たなければならないアプリケーションもあります。
次のサンプル・コードは、TPSENDルーチンの呼出し方法を示しています。
リスト7-2 会話モードでのデータ送信
   . . .
   SET TPNOBLOCK TO TRUE.
   SET TPNOTIME TO TRUE.
   SET TPSIGRSTRT TO TRUE.
   SET TPRECVONLY TO TRUE.
*
   CALL "TPSEND" USING TPSVCDEF-REC
                    TPTYPE-REC
                    DATA-REC
                    TPSTATUS-REC.
   IF NOT TPOK
       error processing . . .
 
メッセージの受信
オープン接続を介して送信されたデータを受信するには、TPRECV(3cbl)ルーチンを使用して次のシグネチャを呼び出します。
01 TPSVCDEF-REC.
COPY TPSVCDEF.
01 TPTYPE-REC.
COPY TPTYPE.
01 DATA-REC.
COPY User Data.
01 TPSTATUS-REC.
COPY TPSTATUS.
CALL "TPRECV" USING TPSVCDEF-REC TPTYPE-REC DATA-REC TPSTATUS-REC.
TPSVCDEF-RECレコードの詳細は、「サービスの定義」を参照してください。TPTYPE-RECレコードの詳細は、3-6ページの「型付きレコードの定義」を参照してください。
次のサンプル・コードは、TPRECVルーチンの使用方法を示しています。
リスト7-3 会話型でのデータ受信
  . . .
  SET TPNOCHANGE TO TRUE.
  SET TPBLOCK TO TRUE.
  SET TPNOTIME TO TRUE.
  SET TPSIGRSTRT TO TRUE.
*
  MOVE LENGTH OF DATA-REC TO LEN.
*
  CALL "TPRECV" USING TPSVCDEF-REC
                   TPTYPE-REC
                   DATA-REC
                   TPSTATUS-REC.
  IF NOT TPOK
      error processing . . .
 
会話の終了
次の場合、接続が切断されて会話が正常に終了します。
単純な会話で、TPRETURNの呼出しが成功した場合
接続が階層構造になった複雑な会話で、一連のTPRETURNの呼出しが成功した場合
グローバル・トランザクションの場合(『C言語を使用したOracle Tuxedo ATMIアプリケーションのプログラミング』「グローバル・トランザクションのコーディング」を参照)
注意:
TPRETURNルーチンの詳細は、『C言語を使用したOracle Tuxedo ATMIアプリケーションのプログラミング』「クライアントおよびサーバーへのリクエスト/レスポンスのコーディング」を参照してください。
次の項では、会話を正常に終了する方法について、2つの例を用いて説明します(これらの会話には、TPRETURN関数を使用するグローバル・トランザクションは含まれていません)。
最初の例では、2つのコンポーネント間の単純な会話を終了する方法を示します。2番目の例では、会話が階層構造になっている複雑な会話を終了する方法を示します。
接続がオープンになっているときに会話を終了すると、エラーが返されます。その場合、TPCOMMITまたはTPRETURNは失敗します。
例: 単純な会話の終了
図7-2は、正常に終了するAとB間の単純な会話を示しています。
図7-2 正常に終了する単純な会話
次の順序で処理が行われます。
1.
Aは、TPSENDONLYを設定してTPCONNECTを呼び出し、接続を設定します(このフラグは、Bが会話の受信側であることを示します)。
2.
Aは、TPRECVONLYを設定してTPSENDを呼び出し、接続の制御をBに移します(その結果、TPEV_SENDONLYイベントが生成されます)。
3.
Bが次にTPRECVを呼び出すと、TP-STATUSTPEEVENTが設定され、TPEVENTTPEV_SENDONLYが戻されて、制御がBに移ったことが示されます。
4.
Bは、TPRETURN-VAL IN TPSVCRETTPSUCCESSを設定してTPRETURNを呼び出します。この呼出しより、Aに対してTPEV_SVCSUCCイベントが生成され、接続が正常に切断されます。
5.
Aは、TPRECVを呼び出して、イベントが発生したことと会話が終了したことを認識します。イベントTPEV_SVCFAILが発生した場合でも、このTPRECVへの呼出しでデータを受信できます。
注意:
この例では、Aはクライアントまたはサーバーのどちらでもかまいませんが、Bはサーバーでなければなりません。
例: 階層構造の会話の終了
図7-3は、正常に終了する階層構造の会話を示しています。
図7-3 接続の階層構造
この例では、サービスBは会話のメンバーで、2番目のサービスCとの接続を開始しています。つまり、A - B間とB - C間という2つのアクティブな接続が存在しています。Bがこの両方の接続を制御している場合にTPRETURNの呼出しを行うと、呼出しは失敗し、すべてのオープン接続にTPEV_SVCERRイベントが通知され、接続が切断されます。
両方の接続を正常に終了するには、次の処理を順に行います。
1.
Bは、Cとの接続にTPRECVONLYフラグを設定してTPSENDを呼び出し、B - C間の接続の制御をCに渡します。
2.
Cは、状況に応じてTPRETURN-VAL IN TPSVCRETTPSUCCESSTPFAILまたはTPEXITを設定して、TPRETURNを呼び出します。
3.
Bは、TPRETURNを呼び出し、Aにイベント(TPEV_SVCSUCCまたはTPEV_SVCFAIL)を通知します。
注意:
会話型サービスは、別のサービスと通信するためにリクエスト/レスポンス型の呼出しを行うことができます。そのため、前述の例では、BからCへの呼出しにTPCONNECTではなくTPCALLまたはTPACALLを使用することもできます。会話型サービスがTPFORWARを呼び出すことはできません。
会話の切断
エラーの発生により切断する唯一の方法はTPDISCON(3cbl)ルーチンを呼び出すことです(「プラグを抜くこと」と同じです)。このルーチンを呼び出すことができるのは、会話のイニシエータ(クライアント)だけです。
注意:
この方法で会話を終了することはお薦めしません。アプリケーションを正常に終了するには、サブオーディネート(サーバー)がTPRETURNルーチンを呼び出す必要があります。
TPDISCONルーチンの呼出しには、次のシグネチャを使用します。
01 TPSVCDEF-REC.
COPY TPSVCDEF.
01 TPSTATUS-REC.
COPY TPSTATUS.
CALL "TPDISCON" USING TPSVCDEF-REC TPSTATUS-REC.
COMM-HANDLE引数は、接続が確立したときにTPCONNECTルーチンによって戻される通信ハンドルを指定します。
TPDISCONルーチンは、接続の相手側のサービスに対してTPEV_DISCONIMMイベントを生成し、COMM-HANDLE無効にします。トランザクションが実行中の場合、そのトランザクションは中断され、データは失われます。
COMM-HANDLEで接続の開始側と識別されていないサービスからTPDISCONが呼び出されると、そのルーチンは失敗し、エラー・コードTPEBADDESCが生成されます。
イベントおよびエラー・コードの全リストとその説明は、『Oracle Tuxedo ATMI COBOL関数リファレンス』「TPDISCON(3cbl)」を参照してください。
会話型のクライアントおよびサーバーのビルド
次のコマンドを使用して、会話型のクライアントおよびサーバーをビルドします。
buildclient()(『C言語を使用したOracle Tuxedo ATMIアプリケーションのプログラミング』の「クライアントのビルド」)
buildserver()(『C言語を使用したOracle Tuxedo ATMIアプリケーションのプログラミング』の「サーバーのビルド」)
会話型サービスとリクエスト/レスポンス型サービスでは、次の操作を行うことはできません。
同じサーバーにクライアントとサーバーを作成すること
クライアントとサーバーに同じ名前を付けること
会話型通信イベントの理解
Oracle Tuxedoシステムの会話型通信では、5つのイベントが認識されます。これらのイベントはすべてTPRECVに通知でき、そのうちの3つはTPSENDにも通知できます。
表7-1は、イベント、そのイベントを受け取るルーチン、および各イベントの詳細な説明を示しています。
 
表7-1 会話型通信イベント
イベント
イベントを受け取る関数
説明
TPEV_SENDONLY
TPRECV
接続の制御が渡されました。この時点で、このプロセスはTPSENDを呼び出すことができます。
TPEV_DISCONIMM
TPSEND
TPRECVTPRETURN
接続はすでに切断され、通信を継続することはできません。TPDISCONルーチンはこのイベントを接続の開始側に通知し、従属サービスとの接続がオープンしたままになっている場合に、TPRETURNが呼び出されると、このイベントをすべてのオープン接続に送信します。接続はエラーが原因で切断されます。トランザクションが存在している場合は、中断されます。
TPEV_SVCERR
TPSEND
接続の開始側が受信し、通常は、従属プログラムが接続の制御を持たない場合に、TPRETURNを呼び出したことを示します。
TPRECV
接続の開始側が受信し、従属プログラムがTPSUCCESSまたはTPFAIL、および妥当なデータ・バッファを使用してTPRETURNを呼び出したが、エラーが発生して呼出しが完了しなかったことを示します。
TPEV_SVCFAIL
TPSEND
接続の開始側が受信し、従属プログラムが接続の制御を持たない場合に、TPRETURNを呼び出し、TPFAILまたはTPEXIT、およびデータなしでTPRETURNが呼び出されたことを示します。
TPRECV
接続の開始側が受信し、従属サービスの処理が正常に終了しなかったこと(つまり、TPRETURNTPFAILまたはTPEXITで呼び出されたこと)を示します。
TPEV_SVCSUCC
TPRECV
接続の開始側が受信し、従属サービスの処理が正常に終了したこと(つまり、TPRETURNTPSUCCESSで呼び出されたこと)を示します。

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