RPGを使ったAPI連携の実際
それでは、RPG を使用した実際のプログラムを紹介しよう(ここで紹介するサービスを実際に利用する際は、各サービスの利用規約に基づいて各自の判断で利用してほしい)。
今回利用するのは、以下の2つの Web サービスである。
◎郵便番号検索:http://zip.cgis.biz
◎翻訳ツール:https://www.deepl.com/pro-api
郵便番号検索は、郵便番号を渡すと、対応する住所を戻してくれるサービスである。クラウドにある郵便番号検索サービスをREST APIで利用する形になる。GET メソッドを使用して郵便番号を送信し、検索結果がXML形式で戻る(CSV形式を選択することも可能)。今回は、QSYS2.HTTP_GET関数を使用して実装する。
次に翻訳ツールは、DeepLが公開しているAPIを無料版で利用する。RPGから翻訳対象の日本語をPOSTメソッドにより送信し、英訳された情報を JSON 形式で受け取る。サンプルでは、SYSTOOLS.HTTPPOSTCLOBVERBOSE関数を使用する。
データ連携―郵便番号検索APIの活用
では郵便番号検索APIを通して、データ連携を実装するサンプルを見てみよう。
まず、http://zip.cgis.biz/ にアクセスして、内容を確認する。APIを利用するプログラムとWeb サービス側の基本的な動きは以下のとおりである。
① 郵便番号をGET送信
② 送信されてきた郵便番号をキーにデータベース(MySQL)を検索
③ 住所情報を含む検索結果をXML/CSV に変換して検索元に戻す
④ 戻ってきた XML/CSV を利用可能な変数等に格納する
RPG側で実装するのは①と④。②と③は郵便番号検索 API が実行する。
API を利用する際のGET送信先URLは、http://zip.cgis.biz/xml/zip.phpである。CSV で受け取りたい場合は、URLのXMLをCSVに変更する(http://zip.cgis.biz/csv/zip.php)。
検索する郵便番号は、上記のURLの後ろにあるznパラメータに続けて指定する。郵便番号100-0001を検索する際のURLと検索結果は、以下のとおりである。
http://zip.cgis.biz/xml/zip.php?zn=1000001
では、ブラウザで上記URLにアクセスし、戻ってくるデータがどのような形式かを確認してみよう。
戻ってくるXMLのデータは、図表6のとおりである。
result要素の各属性には、検索情報と正しく検索できたかどうかなどの情報がセットされている。検索結果の住所は、ADDRESS_value要素内のvalue要素の各属性にそれぞれセットされている。
RPGで郵便番号検索APIにアクセスするために、今回はQSYS2.HTTP_GET関数(https://www.ibm.com/docs/en/i/7.3?topic=functions-http-get)を使用する。
この関数は引数が2つある。最初の引数はアクセスするURL、2番目の引数はJSON形式で指定したHTTPヘッダ情報である。今回の郵便番号APIの仕様には、HTTPヘッダ情報については指定がないので省略する。
図表7の例では、SQLのselectの列名を指定する箇所に、QSYS2.HTTP_GET関数を直接指定している。
この関数の戻り値は前述したXMLデータなので、それをホスト変数xmlAddrにセットしている(into ステートメント)。
ちなみにこのサンプルでは、fromで指定するテーブルがないので、ダミー情報を指定した。これがないと、selectステートメントが完結しないので注意する。
変数xmlAddrにはXMLデータがそのまま入っているので、住所情報(都道府県名や市区町村名など)を個別に利用するには、データの分割と変数へのセットが別途必要になる。XML データの取得とそれをデータ構造にセットする処理をselectステートメントでまとめて行っているサンプルコードが、図表8である。
上記サンプルの select ステートメントが成功すると、郵便番号1000001の検索結果XMLの ADDRESS_value要素の各値が、データ構造Address_valueの関連する各サブフィールドにセットされる。
機能連携―DeepL APIの活用
次にDeepL API を利用して、各国言語を翻訳するサービスをRPGプログラムから呼び出してみよう。
DeepLは2017年にサービスを開始した翻訳エンジンで、サービス当初から他のサービスに比べて翻訳精度が高いと評価されてきた。Google翻訳同様にブラウザに翻訳元のデータを入力し、必要な言語を指定して翻訳結果を入手する以外に、PDFをまるごと翻訳するなどのサービスも提供している。
DeepLが提供する翻訳サービス用のAPI を利用するには、ユーザー登録が必要である。利用プランは無料版(一度に翻訳可能なテキストの文字数の上限が5000字)と、上限なしに翻訳可能な PRO 版(有料)があるが、今回は無料版で利用する。
ユーザー登録に関しては、以下を参考にしてほしい。
・ [DeepL で翻訳しましょう](https://www.deepl.com/ja/pro-api?cta=header-pro-api/) にアクセスし、[無料で登録する]をクリック
・無料版の[無料で登録する]をクリック
・メールアドレスとパスワードを入力して続行
・氏名、住所、API 不正利用防止のためにクレジットカード情報を入力(本人確認が目的であり、Pro版へ手動でアップグレードしない限り、課金は発生しない)
・プランの利用条件に同意し、[無料で登録する]をクリック
・[アカウントを管理する]をクリックし、管理画面に遷移
・アカウントページにて、API で使用する認証キーを確認
アカウントページのアカウント情報タブに表示される認証キーは、APIにアクセスするhttp post 要求時にbodyにセットする必要があるので、確認方法を忘れないように注意する(図表9)。
サンプルのRPGでは、SYSTOOLS.HTTPPOSTCLOBVERBOSEテーブル関数(https://www.ibm.com/docs/ja/i/7.3?topic=ssw_ibm_i_73/rzajq/rzajqudfhttppostclobverbose.html)を使用した。
このテーブル関数に必要な引数は、アクセスするURL、Header情報、リクエスト・メッセージの3つである。テーブル関数なので、結果は図表10の項目を含む表形式で戻ってくる。
それでは、DeepL APIアクセス時に必要な引数について確認していこう。誌面の都合上、基本的な情報のみを解説するが、詳細はDeepLのAPI解説ページ(https://www.deepl.com/docs-api/introduction/)を参考にしてほしい。
まずアクセスするURLは、https://api-free.deepl.com/v2/translateである。前述の郵便番号検索APIがGETメソッドだったのに対し、DeepL APIはPOSTメソッドでアクセスする必要があるので、APIに渡す値はURLには指定しない。
次にHeader情報を見てみよう。Header情報はXMLで記述する必要がある(これはSYSTOOLS.HTTPPOSTCLOBVERBOSE テーブル関数の仕様)が、何を指定すべきかはDeepL APIで決められている。
◎コンテンツタイプ(Content-Type)
application/x-www-form-urlencoded を指定
◎コンテンツ長(Content-Length)
リクエストボディのバイト数を指定
コンテンツ長は3番目の引数であるリクエスト・メッセージの長さなので、翻訳元の文字列によって変化することに注意が必要である。
では、実際のHeader情報を作成するサンプルコードを図表11で見てみよう。
この例では、リクエスト・メッセージをセットした変数の名前がbodyであるとして記述している。
続いて、リクエスト・メッセージ(変数body)にセットする内容を確認しよう。リクエスト・メッセージには、認証キー(auth_key)、翻訳対象文字列(text)、翻訳したい言語の指定(target_lang)と、少なくとも3つの情報を指定する必要がある。
これら3つの情報を、<カッコ内のキー=値>で指定し、それぞれを&で連結した文字列をリクエスト・メッセージに指定する。たとえば、アクセスキーが「b16abxxc-ffff-8bcc-111c-00ad6f222d57:fx」で、翻訳対象文字列が「トンネルを抜けるとそこは雪国だった。」、翻訳したい言語が英語の場合のリクエスト・メッセージは図表12となる。
言語指定は、DE(ドイツ語)、FR(フランス語)、IT(イタリア語)などが可能である。
リクエスト・メッセージを作成するRPGのサンプルコードは、図表13のようになる。
この Body に設定した長さをHeader情報に含める必要があるので、実際のコーディングはBody変数に含めるリクエスト・メッセージを先に作成し、そのあとでHeaderに含めるXML文字列を作成する必要がある。
リクエスト・メッセージとHeader情報を作成し、DeepL APIの翻訳サービスを利用するまでのサンプルコードを図表14に示す(重要部分のみ)。
SYSTOOLS.HTTPPOSTCLOBVERBOSEはテーブル関数なので、selectステートメントのfrom にtable関数の引数として指定する。検索した結果の各カラムの内容はそれぞれ、replyStmf および replyHdr 変数にセットされる。
replyStmfはJSON 形式、replyHdrはXML 形式のデータが保管されるので、このあとにそれぞれを専用の関数もしくはRPGステートメントで分解して、プログラム変数にセットする必要がある。
以上、2つの Web サービスを題材に、RPG プログラムからそのサービスを利用するサンプルコードを解説してきた。もちろんこれ以外のWebサービスも同様に利用できるので、多様なサービスをRPGから利用することを検討してほしい。IBM i だけでは困難だったことも、利用するサービス次第では実現可能になるはずである。
また本稿ではコードを抜粋して解説したが、DeepL API を利用したプログラムは本号の特集「Code for IBM i」で、ツールを使う際のサンプルコードとしても紹介しているので、そちらもぜひ参照してほしい。
REST API を利用するRPGプログラムは、言語の文法だけでなく、TCP/IP 通信に関する知識や連携するデータ形式などの理解も必要で、そのハードルは決して低くはない。学習コストは相応に必要なので、独自に開発する場合はそのコストも考慮に入れて取り組む必要がある。
・・・・・
本稿で紹介したプログラムは 2022年12月時点での Web サービス情報に基づいており、将来APIの仕様が変更になったり、Web サービスそのものが停止になる可能性もあるので、留意されたい。また各プログラムについては、以下の利用環境での実行結果であり、すべての IBM i のバージョンで動作を保証するものではない。
◎利用環境
バージョン:IBM i 7.3
累積PTF:C9116730
Technology Reflesh:6
SF99703(Db2 for i):レベル 32
個別PTF:5770WDS-SI62605
QCCSID:5035
著者
小川 誠 氏
ティアンドトラスト株式会社
代表取締役社長、CIO、CTO
https://www.tat.co.jp/
1989年、エス・イー・ラボ入社。その後、1993年にティアンドトラストに入社。システム/38 から IBM i まで、さまざまな開発プロジェクトに参加。またAS/400 、IBM i の機能拡張に伴い、他プラットフォームとの連携機能開発も手掛ける。IBM i 関連の多彩な教育コンテンツの作成や研修、セミナーなども担当。2021年6月から現職。
[i Magazine・IS magazine] https://www.imagazine.co.jp/