4.1.2 サービス定義
サービス定義は,次のUAPからSPP.NET,またはSPPに対してサービス定義を使用してRPCを実行する場合に定義します。
-
SPP.NET
-
SUP.NET
-
CUP.NET(Connector .NETを利用してSPP.NET,またはSPPにサービスを要求するアプリケーションを含みます)
サービス定義は,サービス定義のファイルとサービス定義が参照するデータ型定義のファイルから構成されます。この節では,サービス定義の定義方法の詳細について説明します。サービス定義を使用したRPCについては,「1.3.2(2) サービス定義(カスタムレコード)を使用したRPC」を参照してください。
- 〈この項の構成〉
(1) データ型定義ファイル
データ型定義とは,RPCでやり取りされる入力データや出力データの形式をメッセージ単位で定義するものです。
サービス定義から参照するデータ型定義ファイルは,次に示す形式で独立したファイルとして定義します。
(a) 形式
struct データ型定義名称 { データ型 メンバ名称[配列指定]; 〔〔データ型 メンバ名称[配列指定];〕…〕 }; 〔〔struct データ型定義名称 { データ型 メンバ名称[配列指定]; 〔〔データ型 メンバ名称[配列指定];〕…〕 };〕…〕
(b) 説明
- ●データ型定義名称 〜〈31文字以内の識別子〉
-
データ型定義に付ける名称を指定します。
指定された名称がカスタムレコードクラスのクラス名となります。
- ●データ型
-
メンバ名称で示される変数に対するデータ型を指定します。
クライアントスタブ生成コマンド(spp2cstub)は,定義された各メンバのデータ型を次の表に示すように,.NET Frameworkのデータ型に対応づけてカスタムレコードクラスを生成します。
また,データの内容を次の表に示すように変換します。
表4‒4 データ型の変換規則と変換内容 データ型定義ファイルで定義されたデータ型
データ型の説明
カスタムレコードクラスで定義される.NET Frameworkのデータ型
データ変換の内容
char
文字列
System.String
charは.NET FrameworkのSystem.Stringに対応づけられます。カスタムレコードを入力データとして使用する場合,スタブ生成コマンドに指定したエンコード方式に従ってバイト配列に変換しデータを扱います。
バイト配列に変換した結果が32バイトで,データ型定義がchar a[30]の場合,2バイトは破棄されます。
int
32ビット符号付き整数
System.Int32
intは.NET FrameworkのSystem.Int32に対応づけられます。
カスタムレコードを入力データとして使用する場合,スタブ生成コマンドに指定されたエンディアンでバイト配列に変換して,RPCの要求メッセージに設定します。
カスタムレコードを出力データとして使用する場合,応答メッセージから4バイトをスタブ生成コマンドに指定されたエンディアンで読み込み,データにセットします。
short
16ビット符号付き整数
System.Int16
shortは.NET FrameworkのSystem.Int16に対応づけられます。カスタムレコードを入力データとして使用する場合,指定されたエンディアンでバイト配列に変換して,RPCの要求メッセージに設定します。
カスタムレコードを出力データとして使用する場合,RPCの応答メッセージから2バイトをスタブ生成コマンドに指定されたエンディアンで読み込み,データにセットします。
long
32ビット符号付き整数
System.Int32
longは.NET FrameworkのSystem.Int32に対応づけられます。
カスタムレコードを入力データとして使用する場合,スタブ生成コマンドに指定されたエンディアンでバイト配列に変換して,RPCの要求メッセージに設定します。
カスタムレコードを出力データとして使用する場合,応答メッセージから4バイトをスタブ生成コマンドに指定されたエンディアンで読み込み,データにセットします。
byte
バイナリデータ
System.Byte
byteは.NET FrameworkのSystem.Byteに対応づけられます。
一次元配列指定にだけ使用できます。
struct
構造体
class(インナークラス)
データ型定義でstructとして定義されるデータ型のことを構造体と呼びます。
structはインナークラスに対応づけられます。
データ型がint,long,またはstructの場合は,先頭からのオフセットが4の整数倍でなければなりません。また,shortの場合は,先頭からのオフセットが2の整数倍でなければなりません。
なお,スタブ生成コマンドでは,自動的にバウンダリ調整をしないため,先頭からのオフセットが正しい整数倍でない場合,エラーとなるので注意が必要です。
バウンダリ調整については,「(d) バウンダリ調整」を参照してください。
データ型がstructの場合は,次に示すように定義します。
struct 構造体名称 { データ型 メンバ名称[配列指定]; 〔〔データ型 メンバ名称[配列指定];〕…〕 } メンバ名称[配列指定];
データ型定義でstructとして定義されるメンバは,その構造体名称がそのままインナークラスのクラス名称になり,メンバ名称がインナークラスの型を持つプロパティ名称になります。
ここで指定するデータ型,メンバ名称,配列要素数はデータ型定義に従います。また,この構造体のデータ型定義先頭からのオフセットは,4の整数倍でなければなりません。また,構造体自身のサイズも4の整数倍でなければなりません。
ただし,構造体を構成するメンバ(構造体の中に構造体がある場合は,そのメンバも含む)がすべてcharまたはbyteの場合は,任意のオフセットおよび任意のサイズを定義できます。
データ型定義でstructとして定義される配列型は,可変長構造体配列として扱えます。可変長構造体配列については,「(e) 可変長構造体配列」を参照してください。
- ●構造体名称 〜〈31文字以内の識別子〉
-
構造体に付ける名称を指定します。
構造体名称の先頭文字は半角英字とします。2文字目以降は半角英数字および半角アンダスコア(_)が使用できます。
- ●メンバ名称 〜〈31文字以内の識別子〉
-
メンバ名称を指定します。
メンバ名称の先頭文字は半角英字で指定してください。
- ●配列指定
-
配列要素数 〜〈符号なし整数〉((1〜8388608))
メンバがデータ型の配列の場合,配列要素数を指定します。
データ型がint,short,long,またはstructのときは,一次元配列が指定できます(配列指定なしも指定できます)。
データ型がbyteのときは,一次元配列だけ指定できます。
データ型がcharのときは,二次元配列まで指定できます。
- 一次元配列
[配列要素数]
- 二次元配列
[配列要素数][配列要素数]
(c) データ型定義の定義例
struct in_data { long I_basho[3]; long I_kakaku; long I_tokuchou; }; struct out_data { char o_name[20]; char o_basho[16]; char o_tokuchou[20]; long o_kakaku; char o_inf[80]; }; struct out_data2 { char o_name[20]; char o_basho[16]; char o_tokuchou[20]; long o_kakaku; char o_inf[80][20]; }; struct put_data { int o_num; struct data { char o_name[20]; char o_basho[16]; char o_tokuchou[20]; long o_kakaku; char o_inf[80]; } data_t[100]; };
(d) バウンダリ調整
バウンダリ調整とは,データ型定義の各変数を決められたバイト境界に配置することをいいます。バウンダリ調整は,コンパイラが自動的に行います。
例えば,次に示すような構造体を使用している場合,先頭からのオフセットを正しくするため,実際はOS,およびコンパイラによって,dataとnumの間に1バイトの補正が入ります。
- 構造体の定義例
struct s_data { char data[3]; long num; } s_data_t
- バウンダリ調整後の定義例
struct s_data { char data[3]; <1バイト> long num; } s_data_t
この例の場合には,次のように修正して使用してください。
- 修正前
struct s_data { char data[3]; long num; } s_data_t;
- 修正後
struct s_data { char data[3]; char wk; long num; } s_data_t;
- ポイント
-
OpenTP1 for .NET Framework以外のOpenTP1システムで使用していた構造体をデータ型定義として使用する場合などは,バウンダリ調整に注意してください。
(e) 可変長構造体配列
データ型がstructで,配列型の場合は,可変長構造体配列として扱えます。可変長構造体配列は次に示す形式で定義します。
- 可変長構造体配列の形式
int 配列要素数を示すメンバ名称 struct 構造体名称 { データ型 メンバ名称[配列指定]; 〔〔データ型 メンバ名称[配列指定];〕…〕 } メンバ名称[配列要素数を示すメンバ名称:配列の最大要素数];
可変長構造体配列を指定する場合は,可変長構造体配列の配列要素数を「データ型がint型の配列要素数を示すメンバ名称:配列の最大要素数」という形式で記述します。構造体名称,データ型,メンバ名称および配列指定については,「(b) 説明」を参照してください。
- 可変長構造体配列の定義例
struct put_data { int o_num; struct data{ char o_name[20]; char o_basho[16]; char o_tokuchou[20]; long o_kakaku; char o_inf[80]; } data_t[o_num:100]; };
可変長構造体配列を使用する場合は,次の点に注意してください。
-
配列要素数を示すメンバ名称は可変長構造体配列より前に定義してください。
-
配列要素数を示すメンバ名称の値は配列の最大要素数に指定した値以下にしてください。配列要素数を示すメンバ名称の値が配列の最大要素数に指定した値を超える場合はエラーが発生します。
-
可変長構造体配列を使用する場合は,構造体の長さは配列の最大要素数に指定した値で計算されるので,配列の最大要素数を指定するときはデータ型定義の長さが1から8388608バイトの範囲になるように指定してください。ただし,RPC送受信メッセージの最大長拡張機能を使用しない場合は,データ型定義の長さは1から1048576バイトの範囲になるように指定してください。
-
生成されたカスタムレコードを使用する場合,可変長構造体配列に対応するプロパティには,配列の最大要素数以内の構造体配列を指定してください。nullまたは配列の最大要素数を超える構造体配列を指定した場合は,TP1MarshalException例外が発生します。
(f) 注意事項
-
データ型定義では任意の位置にコメントを記述できます。コメントは「/*」で始め,「*/」で終了します。なお,コメントのネストはできません。
-
データ型定義全体の長さは1から8388608バイトの範囲になるように記述してください。ただし,RPC送受信メッセージの最大長拡張機能を使用しない場合は,1から1048576バイトの範囲になるように記述してください。
-
データ型定義ファイルでは,1文を複数行にわたって指定しないでください。
-
データ型定義名称としてdcおよびDCで始まる名称は使用しないでください。
-
データ型定義名称,メンバ名称としてクライアントスタブおよびカスタムレコードクラスを生成するプログラム言語のキーワードは使用できません。
-
生成されたカスタムレコードを使用する場合,配列および固定長構造体配列に対応するプロパティには要素数分の配列数を指定してください。nullまたは要素数分以外の配列数を指定した場合は,TP1MarshalException例外が発生します。
-
一つのデータ型定義に同じ名前のメンバ名称を指定しないでください。
(2) サービス定義ファイル
サービス定義とは,サービスの入出力データに対応するデータ型定義を定義するものです。
サービス定義ファイルは,次に示す形式で独立したファイルとして定義します。
(a) 形式
#include "データ型定義ファイル名" 〔〔#include "データ型定義ファイル名"〕 …〕 interface サービス定義名称 { サービス名称(入力データ型定義名, 出力データ型定義名); 〔〔サービス名称(入力データ型定義名, 出力データ型定義名);〕…〕 }
(b) 説明
- ●データ型定義ファイル名 〜〈ファイル名〉
-
このサービス定義で参照するデータ型定義が定義されているファイル名を指定します。ファイル名は次のどちらかの形式で指定します。
-
拡張子を含んだファイル名だけを指定する。
-
相対パスまたは絶対パスを含んだファイル名で指定する。
なお,パス指定時の区切り文字には「/」または「\」が使用できます。
-
- ●サービス定義名称 〜〈31文字以内の識別子〉
-
このサービス定義に付けるサービス定義名称を指定します。
任意に名称を付けることができます。デフォルトではこの名称からクライアントスタブなどのクラス名が生成されます。
- ●サービス名称 〜〈31文字以内の識別子〉
-
このサービス定義に含めるサービス名称を指定します。
対象となるユーザサーバが持つサービス名称を指定してください。
- ●入力データ型定義名 〜〈31文字以内の識別子〉
-
各サービスの入力データに対応するデータ型定義名称を指定します。
入力データ型定義名は,このサービス定義ファイルの#includeディレクティブで指定したデータ型定義ファイルで定義されたデータ型定義名称でなければなりません。
- ●出力データ型定義名 〜〈31文字以内の識別子〉
-
各サービスの出力データに対応するデータ型定義名称を指定します。
出力データ型定義名は,このサービス定義ファイルの#includeディレクティブで指定したデータ型定義ファイルで定義されたデータ型定義名称でなければなりません。
ただし,出力データがない場合は,出力データ型定義名にはDC_NODATAを指定してください(非応答型RPCの場合だけ使用できます)。
(c) サービス定義の定義例
サービス定義の定義例1(業務1のサービス定義)
#include "mydata.h" /* 業務1のサービス定義 */ interface GYOUMU1 { GETDATA1(in_data, out_data); GETDATA2(in_data, out_data2); }
サービス定義の定義例2(業務2のサービス定義)
#include "datas/mydata.h" /* 業務2のサービス定義 */ interface GYOUMU2 { GET_DATA1(in_data, out_data); PUT_DATA1(put_data, DC_NODATA); /* 非応答型 */ }
データ型定義の定義例(mydata.h)
struct in_data { long I_basho[3]; long I_kakaku; }; struct out_data { char o_name[20]; char o_basho[16]; long o_kakaku; char o_inf[80]; }; struct out_data2 { char o_name[20]; char o_basho[16]; long o_kakaku; char o_inf[80][20]; }; struct put_data { int o_num; struct data { char o_name[20]; char o_basho[16]; long o_kakaku; char o_inf[80]; } data_t[100]; };
(d) 注意事項
-
サービス定義では任意の位置にコメントを記述できます。コメントは「/*」で始め,「*/」で終了します。なお,コメントのネストはできません。
-
コメント文中に「//」は使用できません。