ステップ7. iiiFN07サーバー・データベース・ロジックとSET機能をコード化する
このステップでは、部門名称を取得するデータベース・ファイルDEPTABにアクセスするRDMLXを作成し、サーバー側SETのRDMLXを作成します。
1. 作業リスト定義DEPTMEN_Wに従い、フィールドDEPTESCを含む別の作業リストDEPTDES_Wを定義します。これは返されるリストです。両方のリストを消去するコードを追加します。コードは以下のようになります。
*以下のリストがxmlバインディング・マップで使用される
DEF_LIST NAME(#DEPTMEN_W) FIELDS(#DEPTMENT) TYPE(*WORKING)
DEF_LIST NAME(#DEPTDES_W) FIELDS(#DEPTMENT #DEPTDESC) TYPE(*WORKING)
CLR_LIST #DEPTMEN_W
CLR_LIST NAME(#DEPTDES_W)
注:省略値では、作業はこのアプリケーションに適切な50エントリーで定義されます。
2. ファンクションiiiFN07の処理を続けます。受信ロジックの後に以下を追加する必要があります。コメント行の前にコードを追加します。
* HTTP応答内容を作成するサービスをバインドする
以下を行うRDMLXコードを作成します。
a. リスト#DEPTMEN_W (クライアントから受信した作業リスト)から部門コードをSELECT (選択)します。
b. キー#DEPTMENTでファイルDEPTABからフィールド#DEPTDESC (部門名称)をFETCH (取得)します。FETCH操作のI/O状態をチェックします。*OKAY以外の場合、部門名称をリテラル'Department not found'に変更します。
c. 部門名称の作業リスト#DEPTDES_WにエントリーをADD (追加)します。
d. ENDSELECT
RDMLXコードは以下のように表示されます。
SELECTLIST NAMED(#DEPTMEN_W)
**********
FETCH FIELDS(#DEPTDESC) FROM_FILE(DEPTAB) WITH_KEY(#DEPTMENT)
IF_STATUS IS_NOT(*OKAY)
CHANGE FIELD(#DEPTDESC) TO('DEPARTMENT NOT FOUND')
ENDIF
ADD_ENTRY TO_LIST(#DEPTDES_W)
ENDSELECT
**********
3. REVERSE組み込み関数を使用して、#STD_TEXTの内容を逆にするRDMLXを作成します。Trim組み込み関数を使用して、テキスト内の先頭または末尾の余白を削除します。
RDMLXコードは以下のように表示されます。
********** REVERSE THE STRING
#STD_TEXTS
:= #STD_TEXTS.Reverse.Trim
**********
4. スタジオ・プロジェクトで、フォルダーXML List Response/Sample/RDMLXを展開し、ファイルSAMPLE_RDMLX_OUTBOUND_HTTP.TXTをダブルクリックしてテスト・エディタで開きます。
5. 強調表示されたコードを選択します。
6. ファンクションiiiFN07の以下のコードを上記のコードで置き換えます。
* 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)
7. 追加されたコードで、リスト名DEPARTMENTをDEPTDES_Wで置き換え、単語全体のみを置き換えます。
8. CHECKサブルーチンで、エラーが発生した場合はプログラムが終了するようにABORTコマンドをIF..ENDIFステートメントに追加します。
9. ファンクションをコンパイルします。IBM i のJSMサーバーを使用している場合は、ファンクションを登録してIBM i でコンパイルします。
完了したRDMLXコードは以下のように表示されます。
FUNCTION OPTIONS(*DIRECT)
*以下のフィールドがxmlバインディング・マップで使用される
* #DEPTMENT
*
#STD_TEXTS
*以下のフラグメントがxmlバインディング・マップで使用される
GROUP_BY NAME(#LISTREQ)
FIELDS(#STD_TEXTS)
*以下のリストがxmlバインディング・マップで使用される
DEF_LIST NAME(#DEPTMEN_W)
FIELDS(#DEPTMENT) TYPE(*WORKING)
DEF_LIST NAME(#DEPTDES_W) FIELDS(#DEPTMENT
#DEPTDESC) TYPE(*WORKING)
CLR_LIST NAMED(#DEPTMEN_W)
CLR_LIST
NAMED(#DEPTDES_W)
*サービスを開く
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(IIIPRO05_REQUEST) TYPE(*INBOUND) BINDTRACE(*YES)')
USE
BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS
#JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS
#JSMXMSG)
*フラグメントを取得する - DEPARTMENTLISTREQUEST
CHANGE FIELD(#JSMXCMD)
TO('GET FRAGMENT(DEPARTMENTLISTREQUEST) SERVICE_EXCHANGE(*FIELD)')
USE
BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS
#JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS
#JSMXMSG)
*リストを取得する - DEPARTMENT
CHANGE FIELD(#JSMXCMD) TO('GET
LIST(DEPARTMENT)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD)
TO_GET(#JSMXSTS #JSMXMSG #DEPTMEN_W)
EXECUTE SUBROUTINE(CHECK)
WITH_PARMS(#JSMXSTS #JSMXMSG)
SELECTLIST NAMED(#DEPTMEN_W)
*
FETCH
FIELDS(#DEPTDESC) FROM_FILE(DEPTAB) WITH_KEY(#DEPTMENT)
IF_STATUS
IS_NOT(*OKAY)
CHANGE FIELD(#DEPTDESC) TO('DEPARTMENT NOT
FOUND')
ENDIF
ADD_ENTRY
TO_LIST(#DEPTDES_W)
ENDSELECT
*
*文字列を逆にする
#STD_TEXTS :=
#STD_TEXTS.Reverse.Trim
*
* <<<アウトバウンド・バインディング・ロジックをここに記載
>>>
*
* HTTP要求内容を作成するサービスをバインドする
CHANGE FIELD(#JSMXCMD)
TO('BIND SERVICE(IIIPRO05_RESPONSE) TYPE(*OUTBOUND)')
USE
BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS
#JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS
#JSMXMSG)
*フラグメントを設定する - DEPARTMENTLISTRESPONSE
CHANGE FIELD(#JSMXCMD)
TO('SET FRAGMENT(DEPARTMENTLISTRESPONSE) SERVICE_EXCHANGE(*FIELD)')
USE
BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD) TO_GET(#JSMXSTS
#JSMXMSG)
EXECUTE SUBROUTINE(CHECK) WITH_PARMS(#JSMXSTS
#JSMXMSG)
*リストを設定する - DEPARTMENT
CHANGE FIELD(#JSMXCMD) TO('SET
LIST(DEPARTMENT)')
USE BUILTIN(JSMX_COMMAND) WITH_ARGS(#JSMXHDLE1 #JSMXCMD)
TO_GET(#JSMXSTS #JSMXMSG #DEPTDES_W)
EXECUTE SUBROUTINE(CHECK)
WITH_PARMS(#JSMXSTS #JSMXMSG)
*内容を書き込む
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)
*ルーチンをチェックする
SUBROUTINE NAME(CHECK)
PARMS((#JSMXSTS *RECEIVED) (#JSMXMSG *RECEIVED))
IF COND('#JSMXSTS *NE
OK')
USE BUILTIN(JSMX_CLOSE) WITH_ARGS(#JSMXHDLE1) TO_GET(#JSMXSTS
#JSMXMSG)
ABORT
ENDIF
ENDROUTINE