ステップ 7. iiiFN06 サーバーのデータベース・ロジックと SET 機能をコーディングする
INT007 - 部門&社員サーバー
このステップでは、論理ビュー PSLMST1 (部門ごとの人事) を使用して社員リストを取得するための選択 (SELECT) を行い、その後、ファイル PSLSKL (人事スキル) で社員のスキル・リストを取得するための選択 (SELECT) を実行する RDMLX を作成します。サーバー側の設定 (SET) を行う RDMLX は、この内部ロジック中でインラインで行われます。これは、内部ロジックとSETコマンドが順に分けられていた以前の演習とは異なります。
この演習では、内部ロジックの終了後、各コマンドを順番に実行しません。代わりに、アウトバウンドBINDとルート・フラグメントSETが、インバウンドBINDコマンドとGETコマンドの直後に来ます(データベース・アクセスの前)。さらに2つのSETコマンドが、外部のSELECTステートメントに入ります。最後に、WRITEコマンドとSENDコマンドが最後のENDSELECTの後に続きます。
iiiFN06 ファンクションの全体の構造は次のようになります。
1. JSMX_OPEN |
a. PSLSKL に対する SELECT |
8. ENDSELECT |
1. ファンクション iiiFN06 で、以下のコードを探して削除します。
- サービスをバインドして HTTP 応答コンテンツを作成
CHANGE FIELD(#JSMXCMD) TO('BIND SERVICE( <<<outbound.class>>> ) TYPE(*OUTBOUND)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
2. プロジェクト iii 研修 がスタジオで開かれている状態で、サーバー XML 社員要求/Samples/RDMLX フォルダの SAMPLE_RDMLX_OUTBOUND_HTTP.txt ファイルをテキスト・エディターで開きます。以下に示されているコードを探します。
赤で示されているコードをコピーしてファンクションに貼り付け、削除したコード・ブロックと置き換えます。
3. EMPWORK という作業リスト定義を、フィールド SKILDESC を含むファンクションの上部に追加します。これは、返される各社員のスキル・リストです。コードは以下のようになります。 DEF_LIST NAME(#EMPWORK) FIELDS(#SKILDESC) TYPE(*WORKING) ENTRYS(*MAX)
4. アウトバウンドの BIND と SET のロジックを追加したら、以下の操作を行う RDMLX コードを作成します。
a. キー・フィールド DEPTMENT を使用して、論理ファイル PSLMST1 から社員番号と名前を選択 (SELECT) します。
b. この SELECT 処理内で、名と姓からフルネームのフィールドを設定します。
c. さらにこの SELECT ループ内で、CLR_LIST EMPWOR を行った後、KPSLSKL に対して、SELECT を実行し、社員番号を使って各社員のスキル・コードのリストを取得します。
d. 内部の (ネストされた) SELECT 内で、各スキル・コードについて SKLTAB からスキルの説明を取得 (FETCH) します。
e. 社員のスキル作業リスト EMPWORK にエントリーを追加 (ADD) します。
f. .両方の SELECT を終了 (END) します。
RDMLX コードは以下のようになります。
SELECT FIELDS(#EMPNO #SURNAME #GIVENAME) FROM_FILE(PSLMST1) WITH_KEY(#DEPTMENT)
#FULLNAME := #GIVENAME ' ' #SURNAME
CLR_LIST NAMED(#EMPWORK)
SELECT FIELDS(#SKILCODE) FROM_FILE(PSLSKL) WITH_KEY(#EMPNO)
FETCH FIELDS(#SKILDESC) FROM_FILE(SKLTAB) WITH_KEY(#SKILCODE)
ADD_ENTRY TO_LIST(#EMPWORK)
ENDSELECT - 社員フラグメント設定
- 社員スキルリスト設定
ENDSELECT
注意:次のステップで分かりやすいように、このコードにはコメントが付けられています。
5. 前回と同様、SAMPLE_RDMLX_OUTBOUND_HTTP.txt ファイルのこの演習用に生成されたコードを使って、ファンクションを完成させます。以下に示されているコードを探します。
6. 上に示されたコピーしてコードに貼り付け、ステップ 4f で以下のコメント部分を置き換えます。 - 社員フラグメント設定
- 社員スキルリスト設定
7. リスト #EMPWORK を参照するように、TO_GET() キーワードの作業リスト名を変更します。 コードは以下のようになります。 - リストの設定 - EMPLOYEESKILL
CHANGE FIELD(#JSMXCMD) TO('SET LIST(EMPLOYEESKILL)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG #EMPWORK)
8. ファンクションの RDMLX コードと、その後に続く最後の ENDSELECT を確認します。最初にコピーした生成済みコードに、必要なWRITE、SEND、CLOSEロジックが含まれています。
9. CHECK サブルーチンで、エラーが発生した場合はプログラムが終了するように .ENDIF ステートメントに ABORT コマンドを追加します。
10. ファンクション iiiFN06 を保存してコンパイルします。IBM i の JSM サーバーを使用している場合は、ファンクションを IBM iにチェックインしてコンパイルします。
完了した RDMLX コードは以下のようになります。
FUNCTION OPTIONS(*DIRECT) - 以下のフィールドは xml バインド・マップで使用
- #DEPTMENT
- 以下のフラグメントは xml バインド・マップで使用
GROUP_BY NAME(#DEPTREQ) FIELDS(#DEPTMENT)
*
DEF_LIST NAME(#empwork) FIELDS(#skildesc) TYPE(*WORKING) ENTRYS(*MAX)
- サービスを開く
USE BUILTIN(JSMX_OPEN) TO_GET(#JSMXSTS #JSMXMSG #JSMXHDLE1)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- サービスのロード
CHANGE FIELD(#JSMXCMD) TO('SERVICE_LOAD SERVICE(HTTPInboundXMLBindService) SERVICE_CONTENT(*HTTP) TRACE(*YES)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- サービスをバインドして、HTTP 要求コンテンツを読み込む
CHANGE FIELD(#JSMXCMD) TO('BIND SERVICE(IIIPRO06_REQUEST) TYPE(*INBOUND) BINDTRACE(*YES)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- フラグメント取得 - DEPARTMENTREQUEST
CHANGE FIELD(#JSMXCMD) TO('GET FRAGMENT(DEPARTMENTREQUEST) SERVICE_EXCHANGE(*FIELD)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- サービスをバインドして、HTTP 要求コンテンツを作成
CHANGE FIELD(#JSMXCMD) TO('BIND SERVICE(IIIPRO06_RESPONSE) TYPE(*OUTBOUND)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- フラグメント設定 - EMPLOYEELIST
CHANGE FIELD(#JSMXCMD) TO('SET FRAGMENT(EMPLOYEELIST) SERVICE_EXCHANGE(*FIELD)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
SELECT FIELDS(#EMPNO #SURNAME #GIVENAME) FROM_FILE(PSLMST1) WITH_KEY(#DEPTMENT)
#FULLNAME := #GIVENAME + ' ' + #SURNAME
CLR_LIST NAMED(#EMPWORK)
SELECT FIELDS(#SKILCODE) FROM_FILE(PSLSKL) WITH_KEY(#EMPNO)
FETCH FIELDS(#SKILDESC) FROM_FILE(SKLTAB) WITH_KEY(#SKILCODE)
ADD_ENTRY TO_LIST(#EMPWORK)
ENDSELECT - フラグメント設定 - EMPLOYEE
CHANGE FIELD(#JSMXCMD) TO('SET FRAGMENT(EMPLOYEE) SERVICE_EXCHANGE(*FIELD)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- リスト設定 - EMPLOYEESKILL
CHANGE FIELD(#JSMXCMD) TO('SET LIST(EMPLOYEESKILL)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG #EMPWORK)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
ENDSELECT
- コンテンツの書き込み
CHANGE FIELD(#JSMXCMD) TO('WRITE INDENT(*YES) BINDTRACE(*YES)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- HTTP 応答コンテンツの送信
CHANGE FIELD(#JSMXCMD) TO('SEND')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- サービスを閉じる
USE BUILTIN(JSMX_CLOSE) WITH_ARGS(#JSMXHDLE1) TO_GET(#JSMXSTS #JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS #JSMXMSG)
- Check ルーチン
SUBROUTINE NAME(CHECK) PARMS((#JSMXSTS *RECEIVED) (#JSMXMSG *RECEIVED))
IF COND('#JSMXSTS *NE OK')
USE BUILTIN(JSMX_CLOSE) WITH_ARGS(#JSMXHDLE1) TO_GET(#JSMXSTS #JSMXMSG)
ENDIF
ENDROUTINE
ファンクション iiiFN06 のコーディングのおさらい - ここまで、ソリューション「サーバー XML 社員要求」のファンクション iiiFN06 の最初のコーディングを SAMPLE_RDMLX_INBOUND_HTTP.txt にあるインバウンドのロジックを使って作成しました。
- * サービスをバインドして HTTP 応答コンテンツを作成のコーディングは削除しました。これは、ソリューション「サーバー XML 社員応答」用に SAMPLE_RDMLX_OUTBOUND_HTTP.txt にあるアウトバウンドのロジックに置き換える必要があるからです。
- SAMPLE_RDMLX_OUTBOUND_HTTP.txt からのコードは以下に追加されました。
- * サービスをバインドして、要求コンテンツを作成
- * フラグメント設定 - EMPLOYEELIST
- 社員のスキル記述のリストを入れる作業リスト EMPWORK を定義しました。
- * フラグメント設定 - EmployeeList, の後に以下を実行するロジックを追加しました。
- 部門コードを使って社員を選択
- 社員番号キーに対する社員スキルを選択
- スキル記述を SKLTAB から取得
- EMPWORK にエントリーを追加
- 社員スキルの select/endselect の後に、SAMPLE_RDMLX_OUTBOUND_HTTP.txt のコードを次の場所にコピーしました。
- * フラグメント設定 - EMPLOYEE
- * リスト設定 - EMPLOYEESKILL
- CHECK_STATUS サブルーチンをエラー時の ABORT に変えました。
事前に作成されていたコードを使ってサーバー・ファンクションを作成して、XML 要求に対するインバウンド・ロジックをすべて処理し、ファイル処理に関する独自のコーディングを追加して要求されたデータを生成するロジックを作成して、応答 XML ドキュメントを作成するアウトバウンド・ロジックを作成しました。