先の説明でXMLとは何かは理解して頂けたと思う。
そしてRPGではXMLをデータ構造(DS)にマッピングする演算命令として
XML-INTO という命令があることも紹介した。
そして現在、IBM関連のサイトでXML-INTOのサンプル・ソースが
紹介されているがそれらのすべては実は動作しない。
これはIBMのRPG解説書やRPGプログラマーの手引きで紹介されているものも
すべて含めて動作しないものである。
正確に言えば日本語環境ではi5/OS Ver7.4であっても動作しない。
それはXML-INTO命令が日本語環境を考慮されていないことに起因している。
日本のサイトで公開しているサンプル・ソースも日本語環境では
全く動作しない。
そこで
CHGJOB CCSID(37)
XML-INTO ….
とするとXML-INTOは動作するがこれではXMLに漢字データが
含まれているとエラーになってこれも正常に動作することができない。
そこで正常にXML-INTOを日本語環境で動作させるようにした
国内で第一号のソースが次のサンプル・ソースである。
[日本語環境で動作する初めてのXML-INTO RPGサンプル: TESTXML ]
ソースはこちらから
0001.00 H DFTNAME(TESTXML) DATEDIT(*YMD/) BNDDIR('QC2LE') 0002.00 H CCSID(*GRAPH:*SRC) 0003.00 F********** XML_INTO のテスト ***************************************** 0004.00 F* 0005.00 F********************************************************************** 0006.00 0007.00 * CRTBNDRPG OBJ(OBJLIB/TESTXML) SRCFILE(MYSRCLIB/QRPGLESRC) 0008.00 * DFTACTRP(*NO) ACTGRP(*NEW) DBGVIEW(*SOURCE) AUT(*ALL) 0009.00 0010.00 *-------------------------------------------------------------------* 0011.00 * 2021/11/27 : 作成 0012.00 *-------------------------------------------------------------------* 0013.00 *( 作業変数 ) 0014.00 D XML S 512C CCSID(1200) 0015.00 0016.00 D RECORD DS QUALIFIED 0017.00 D SHCODE 1 10A 0018.00 D SHNAME 11 34A 0019.00 D SHTANK 35 41S 0 0020.00 D SHSCOD 42 45A 0021.00 0022.00 /FREE 0023.00 XML = %UCS2('+ 0024.00 '); 0029.00 XML-INTO RECORD %XML(XML:'ccsid=ucs2 case=any'); 0030.00 /END-FREE 0031.00 C SETON LR 0032.00 C RETURNNV-CF1 + 0025.00Cカセット編集ビデオ + 0026.0058000 + 0027.000002 + 0028.00
[コンパイル]
CRTBNDRPG PGM(OBJLIB/TESTXML) SRCFILE(MYSRCLIB/QRPGLESRC) DFTACTGRP(*NO)
ACTGRP(*NEW) DBGVIEW(*SOURCE) AUT(*ALL)
[解説]
まず Unicode変数(USC-2)として XML を
0014.00 D XML S 512C CCSID(1200)
のように定義する。変数のタイプは A ではなく C であることに注意。CCSIDは 1200 (=UTF16)である。
次にXMLと同じデータ構造 : RECORD を
0016.00 D RECORD DS QUALIFIED 0017.00 D SHCODE 1 10A 0018.00 D SHNAME 11 34A 0019.00 D SHTANK 35 41S 0 0020.00 D SHSCOD 42 45A
として定義する。データ構造の名前 RECORD とXMLの名前 RECORD は同じにしなければならない。
次にXMLの内容を
0022.00 /FREE 0023.00 XML = %UCS2(<RECORD>+ 0024.00 <SHCODE>NV-CF1<<SHCODE>+ 0025.00 <SHNAME> Cカセット編集ビデオ </SHNAME>+ 0026.00 <SHTANK>58000</SHTANK>+ 0027.00 <SHSCOD>0002</SHSCOD>+ 0028.00 </RECORD>');
として代入するが組込み関数 %UCS2 によって
XMLの中に保管される。
最後に XML-INTO命令を使って
0029.00 XML-INTO RECORD %XML(XML:'ccsid=ucs2 case=any');
のようにしてXMLをデータ構造(DS): RECORD に変換するというわけである。
このとき XML-INTO のオプションとして
ccsid=usc2 の指定によってXMLの値はUTF-16であることを宣言しておくと
XMLのUTF-16からEBCDICのデータ構造へと変換されるのである。
XML-INTO では CCSID 5026, 5035および 1399からの変換はサポートされていない。
唯一、日本語と互換性があるのはUTF-16だけである。
それゆえUTF-16からの変換が指示されていないIBM解説書やIBM特約店がやIBM SEが
紹介しているXML-INTOのサンプル・ソースは全く動作できないのである。
これも実際に実験してみればすぐにわかることであるが
彼等は全くテストもせずにサンプル・ソースとして公開しているのだろう。
もうひとつ case=any とオプション指定しているがXML-INTO のXMLの省略値は
case=lower つまり英子文字を標準としているので
英大文字を使う場合は case=upper または case=any の指定が必要である。
この注意点はどのサイトにも紹介されていない。
つまり彼らは実際に動作させたことがないのである。
実際にデータ構造に展開されているかどうかは
STRDBG でデバッグ・モードで動作させて31行目でデータ構造RECORDを表示させてみれば
確認することができる。
[STRDBG で EVAL RECORD ]
評価式 前のデバッグ式 > EVAL record RECORD.SHCODE = 'NV-CF1 ' RECORD.SHNAME = ' Cカセット編集ビデオ ' RECORD.SHTANK = 0058000. RECORD.SHSCOD = '0002'
これが日本語環境で初めて動作したXML-INTOである。
今回は簡単に文字列からのパースを行ったが次回は実際にIFSからのファイルのXMLを
パースする方法を紹介する。