XML 在 DB2 中解析 - 在单个 XML CLOB 字段中生成多行表达式
XML Parsing in DB2 - Multiple row generating expressions in single XML CLOB field
我的 XML 具有复杂的结构,其中多次出现重复节点(多行生成器)。
查询:
select X.*, A.id
from tbl_with_blob a,
XMLTABLE(
'$XMLDATA//BusData/LOB1/Vehicle' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
--these columns are getting parsed correctly - since they are having only one node
"vehicle_id" varchar(50) PATH '@id'
,"manufacturer" varchar(100) PATH 'let $x := . return $x/Manufacturer/.'
,"loc_ref_id" varchar(100) PATH 'let $x := . return $x/@LocationRef'
--these columns are throwing error - because there are multiple nodes with the same name
,"x_vc1_1" varchar(1000) PATH 'let $x := . return $x/Vehicle_child1/Vehicle_child1_1/.'
,"x_SC1_1" varchar(1000) PATH 'let $x := . return $x/Vehicle_child1/SomeCode1_1/.'
,"x_Vc2_varcd" varchar(1000) PATH 'let $x := . return $x/Vehicle_child2/@varCd'
,"x_vc2_lmitamt" varchar(100) PATH 'let $x := . return $x/Vehicle_child2/Limit/FormatInteger/.'
) as X
where id='<some_id>'
with ur;
XML:
<BusData>
<LOB1>
<Vehicle id="A333" LocationRef="A194">
<Manufacturer id="A306">TOYT<Manufacturer>
<Vehicle_child1 id="A303">
<Vehicle_child1_1 id="A400">RoadSideInd</Vehicle_child1_1>
</Vehicle_child1>
<Vehicle_child1 id="A399">
<Vehicle_child1_1 id="A407">Commercial</Vehicle_child1_1>
<SomeCode1_1 id="A436">NO</SomeCode1_1>
</Vehicle_child1>
<Vehicle_child1 id="A434">
<Vehicle_child1_1 id="A412">VehAgreedValue</Vehicle_child1_1>
<SomeCode1_1 id="A474"/>
<Num id="A476">1000</Num>
</Vehicle_child1>
<Vehicle_child2 id="A411" varCd="47" varSomeLimit="500">
<Vehicle_child2Cd id="A412">COLL</Vehicle_child2Cd>
</Vehicle_child2>
<Vehicle_child2 id="A413" varCd="08" varSomeLimit="300">
<Vehicle_child2Cd id="A501">UMCSL</Vehicle_child2Cd>
<SomeLimit id="A498">
<FormatInteger id="A499">30000<FormatInteger>
</SomeLimit>
</Vehicle_child2>
<Vehicle_child2 id="A503" varCd="0A" varSomeLimit="450">
<Vehicle_child2Cd id="A517">CLMFG</Vehicle_child2Cd>
<SomeLimit id="A521">
<FormatInteger id="A532">6000<FormatInteger>
</SomeLimit>
</Vehicle_child2>
<Vehicle>
</LOB1>
</BusData>
预期输出:
id vehicle_id manufacturer loc_ref_id x_vc1_1 x_SC1_1 x_Vc2_varcd x_vc2_lmitamt
HT56NU4M A333 TOYT A194 RoadSideInd (null) 47 (null)
HT56NU4M A333 TOYT A194 RoadSideInd (null) 08 30000
HT56NU4M A333 TOYT A194 RoadSideInd (null) 0A 6000
HT56NU4M A333 TOYT A194 Commercial NO 47 (null)
HT56NU4M A333 TOYT A194 Commercial NO 08 30000
HT56NU4M A333 TOYT A194 Commercial NO 0A 6000
HT56NU4M A333 TOYT A194 VehValue (null) 47 (null)
HT56NU4M N333 TOYT A194 VehValue (null) 08 30000
HT56NU4M N333 TOYT A194 VehValue (null) 0A 6000
当我使用上述查询时 - 我收到以下错误:
DB2 SQL Error: SQLCODE= -16003, SQLSTATE=10507,SQLERRMC=(item(), item()+);item(), DRIVER=4.23.42
我试图修改 行生成表达式 以将其中一个行生成器包含为 Vehicle_child1,其中为 Vehicle_child1 给出了正确的结果,但是缺少 Vehicle_child2。
我需要同时拥有(实时可能多达 10 或 15 个)行生成器组合并为每次出现提供多行。
任何人都可以帮助我 - 如何在 DB2 的 XMLTABLE 函数中使用多个行生成表达式?
谢谢
LN
试试这个:
/*
WITH tbl_with_blob (ID, XML_COL_TEXT) AS
(
VALUES
('HT56NU4M', XMLPARSE(DOCUMENT '<BusData>
<LOB1>
<Vehicle id="A333" LocationRef="A194">
<Manufacturer id="A306">TOYT</Manufacturer>
<Vehicle_child1 id="A303">
<Vehicle_child1_1 id="A400">RoadSideInd</Vehicle_child1_1>
</Vehicle_child1>
<Vehicle_child1 id="A399">
<Vehicle_child1_1 id="A407">Commercial</Vehicle_child1_1>
<SomeCode1_1 id="A436">NO</SomeCode1_1>
</Vehicle_child1>
<Vehicle_child1 id="A434">
<Vehicle_child1_1 id="A412">VehAgreedValue</Vehicle_child1_1>
<SomeCode1_1 id="A474"/>
<Num id="A476">1000</Num>
</Vehicle_child1>
<Vehicle_child2 id="A411" varCd="47" varSomeLimit="500">
<Vehicle_child2Cd id="A412">COLL</Vehicle_child2Cd>
</Vehicle_child2>
<Vehicle_child2 id="A413" varCd="08" varSomeLimit="300">
<Vehicle_child2Cd id="A501">UMCSL</Vehicle_child2Cd>
<SomeLimit id="A498">
<FormatInteger id="A499">30000</FormatInteger>
</SomeLimit>
</Vehicle_child2>
<Vehicle_child2 id="A503" varCd="0A" varSomeLimit="450">
<Vehicle_child2Cd id="A517">CLMFG</Vehicle_child2Cd>
<SomeLimit id="A521">
<FormatInteger id="A532">6000</FormatInteger>
</SomeLimit>
</Vehicle_child2>
</Vehicle>
</LOB1>
</BusData>'))
)
*/
select A.id, X1.*, X2.*
from
tbl_with_blob a
, XMLTABLE
(
'$XMLDATA/BusData/LOB1/Vehicle/Vehicle_child1' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"vehicle_id" varchar(50) PATH '@id'
, "manufacturer" varchar(100) PATH '../Manufacturer'
, "loc_ref_id" varchar(100) PATH '../@LocationRef'
, "x_vc1_1" varchar(1000) PATH 'Vehicle_child1_1'
, "x_SC1_1" varchar(1000) PATH 'SomeCode1_1'
) X1
, XMLTABLE
(
'$XMLDATA/BusData/LOB1/Vehicle/Vehicle_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"x_Vc2_varcd" varchar(1000) PATH '@varCd'
,"x_vc2_lmitamt" varchar(100) PATH 'SomeLimit/FormatInteger'
) X2;
是的,马克 - 我用你的方法编写了如下查询:
with sub_x1 as
(
select
A.id, X1.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/Vehicle_child1' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"vehicle_id" varchar(50) PATH '@id'
-- and other cols --
) as X1
where id='<some_id>'
),
sub_x2 as
(
select
A.id, X2.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/Vehicle_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"some_code1" varchar(50) PATH '@id'
-- and other cols --
) as X1
where id='<some_id>'
),
sub_x3 as
(
select
A.id, X3.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/some_other_node/s_o_n/some_child1' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"some_other_cd" varchar(50) PATH '@id'
-- and other cols --
) as X3
where id='<some_id>'
),
sub_x4 as
(
select
A.id, X4.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/yet_other_node/y_a_c_n/yet_another_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"yet_other_cd" varchar(50) PATH '@id'
-- and other cols --
) as X4
where id='<some_id>'
),
sub_x5 as
(
select
A.id, X5.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/yet_other_node/y_o_n/yet_another_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"yet_other_cd2" varchar(50) PATH '@id'
-- and other cols --
) as X5
where id='<some_id>'
)
select
X1.<cols>,
X2.<cols>,
X3.<cols>,
X4.<cols>,
X5.<cols>,
from X1, X2, X3, X4, X5
where
X1.id=X2.id
and (X1.id=X3.id and X2.id=X3.id)
and (X1.id=X4.id and X2.id=X4.id and X3.id=X4.id)
and (X1.id=X5.id and X2.id=X5.id and X3.id=X5.id and X4.id=X5.id)
with ur;
这一直持续到 运行,并且每个单独的查询都提供了正确的结果集和唯一的行。 X1 给出 4 行,X2 给出 9,X3 给出 11,X4 给出 7,X5 给出 6。
这些子查询中的每一个都包含 XML XPath,它们在其直接父节点中重复出现 - 多次。
但作为一个整体查询给出了这些的叉积 - 16632 行。
显然我在 JOIN 条件中遗漏了一些东西?
谢谢
LNC
我的 XML 具有复杂的结构,其中多次出现重复节点(多行生成器)。
查询:
select X.*, A.id
from tbl_with_blob a,
XMLTABLE(
'$XMLDATA//BusData/LOB1/Vehicle' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
--these columns are getting parsed correctly - since they are having only one node
"vehicle_id" varchar(50) PATH '@id'
,"manufacturer" varchar(100) PATH 'let $x := . return $x/Manufacturer/.'
,"loc_ref_id" varchar(100) PATH 'let $x := . return $x/@LocationRef'
--these columns are throwing error - because there are multiple nodes with the same name
,"x_vc1_1" varchar(1000) PATH 'let $x := . return $x/Vehicle_child1/Vehicle_child1_1/.'
,"x_SC1_1" varchar(1000) PATH 'let $x := . return $x/Vehicle_child1/SomeCode1_1/.'
,"x_Vc2_varcd" varchar(1000) PATH 'let $x := . return $x/Vehicle_child2/@varCd'
,"x_vc2_lmitamt" varchar(100) PATH 'let $x := . return $x/Vehicle_child2/Limit/FormatInteger/.'
) as X
where id='<some_id>'
with ur;
XML:
<BusData>
<LOB1>
<Vehicle id="A333" LocationRef="A194">
<Manufacturer id="A306">TOYT<Manufacturer>
<Vehicle_child1 id="A303">
<Vehicle_child1_1 id="A400">RoadSideInd</Vehicle_child1_1>
</Vehicle_child1>
<Vehicle_child1 id="A399">
<Vehicle_child1_1 id="A407">Commercial</Vehicle_child1_1>
<SomeCode1_1 id="A436">NO</SomeCode1_1>
</Vehicle_child1>
<Vehicle_child1 id="A434">
<Vehicle_child1_1 id="A412">VehAgreedValue</Vehicle_child1_1>
<SomeCode1_1 id="A474"/>
<Num id="A476">1000</Num>
</Vehicle_child1>
<Vehicle_child2 id="A411" varCd="47" varSomeLimit="500">
<Vehicle_child2Cd id="A412">COLL</Vehicle_child2Cd>
</Vehicle_child2>
<Vehicle_child2 id="A413" varCd="08" varSomeLimit="300">
<Vehicle_child2Cd id="A501">UMCSL</Vehicle_child2Cd>
<SomeLimit id="A498">
<FormatInteger id="A499">30000<FormatInteger>
</SomeLimit>
</Vehicle_child2>
<Vehicle_child2 id="A503" varCd="0A" varSomeLimit="450">
<Vehicle_child2Cd id="A517">CLMFG</Vehicle_child2Cd>
<SomeLimit id="A521">
<FormatInteger id="A532">6000<FormatInteger>
</SomeLimit>
</Vehicle_child2>
<Vehicle>
</LOB1>
</BusData>
预期输出:
id vehicle_id manufacturer loc_ref_id x_vc1_1 x_SC1_1 x_Vc2_varcd x_vc2_lmitamt
HT56NU4M A333 TOYT A194 RoadSideInd (null) 47 (null)
HT56NU4M A333 TOYT A194 RoadSideInd (null) 08 30000
HT56NU4M A333 TOYT A194 RoadSideInd (null) 0A 6000
HT56NU4M A333 TOYT A194 Commercial NO 47 (null)
HT56NU4M A333 TOYT A194 Commercial NO 08 30000
HT56NU4M A333 TOYT A194 Commercial NO 0A 6000
HT56NU4M A333 TOYT A194 VehValue (null) 47 (null)
HT56NU4M N333 TOYT A194 VehValue (null) 08 30000
HT56NU4M N333 TOYT A194 VehValue (null) 0A 6000
当我使用上述查询时 - 我收到以下错误:
DB2 SQL Error: SQLCODE= -16003, SQLSTATE=10507,SQLERRMC=(item(), item()+);item(), DRIVER=4.23.42
我试图修改 行生成表达式 以将其中一个行生成器包含为 Vehicle_child1,其中为 Vehicle_child1 给出了正确的结果,但是缺少 Vehicle_child2。
我需要同时拥有(实时可能多达 10 或 15 个)行生成器组合并为每次出现提供多行。
任何人都可以帮助我 - 如何在 DB2 的 XMLTABLE 函数中使用多个行生成表达式?
谢谢 LN
试试这个:
/*
WITH tbl_with_blob (ID, XML_COL_TEXT) AS
(
VALUES
('HT56NU4M', XMLPARSE(DOCUMENT '<BusData>
<LOB1>
<Vehicle id="A333" LocationRef="A194">
<Manufacturer id="A306">TOYT</Manufacturer>
<Vehicle_child1 id="A303">
<Vehicle_child1_1 id="A400">RoadSideInd</Vehicle_child1_1>
</Vehicle_child1>
<Vehicle_child1 id="A399">
<Vehicle_child1_1 id="A407">Commercial</Vehicle_child1_1>
<SomeCode1_1 id="A436">NO</SomeCode1_1>
</Vehicle_child1>
<Vehicle_child1 id="A434">
<Vehicle_child1_1 id="A412">VehAgreedValue</Vehicle_child1_1>
<SomeCode1_1 id="A474"/>
<Num id="A476">1000</Num>
</Vehicle_child1>
<Vehicle_child2 id="A411" varCd="47" varSomeLimit="500">
<Vehicle_child2Cd id="A412">COLL</Vehicle_child2Cd>
</Vehicle_child2>
<Vehicle_child2 id="A413" varCd="08" varSomeLimit="300">
<Vehicle_child2Cd id="A501">UMCSL</Vehicle_child2Cd>
<SomeLimit id="A498">
<FormatInteger id="A499">30000</FormatInteger>
</SomeLimit>
</Vehicle_child2>
<Vehicle_child2 id="A503" varCd="0A" varSomeLimit="450">
<Vehicle_child2Cd id="A517">CLMFG</Vehicle_child2Cd>
<SomeLimit id="A521">
<FormatInteger id="A532">6000</FormatInteger>
</SomeLimit>
</Vehicle_child2>
</Vehicle>
</LOB1>
</BusData>'))
)
*/
select A.id, X1.*, X2.*
from
tbl_with_blob a
, XMLTABLE
(
'$XMLDATA/BusData/LOB1/Vehicle/Vehicle_child1' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"vehicle_id" varchar(50) PATH '@id'
, "manufacturer" varchar(100) PATH '../Manufacturer'
, "loc_ref_id" varchar(100) PATH '../@LocationRef'
, "x_vc1_1" varchar(1000) PATH 'Vehicle_child1_1'
, "x_SC1_1" varchar(1000) PATH 'SomeCode1_1'
) X1
, XMLTABLE
(
'$XMLDATA/BusData/LOB1/Vehicle/Vehicle_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"x_Vc2_varcd" varchar(1000) PATH '@varCd'
,"x_vc2_lmitamt" varchar(100) PATH 'SomeLimit/FormatInteger'
) X2;
是的,马克 - 我用你的方法编写了如下查询:
with sub_x1 as
(
select
A.id, X1.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/Vehicle_child1' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"vehicle_id" varchar(50) PATH '@id'
-- and other cols --
) as X1
where id='<some_id>'
),
sub_x2 as
(
select
A.id, X2.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/Vehicle_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"some_code1" varchar(50) PATH '@id'
-- and other cols --
) as X1
where id='<some_id>'
),
sub_x3 as
(
select
A.id, X3.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/some_other_node/s_o_n/some_child1' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"some_other_cd" varchar(50) PATH '@id'
-- and other cols --
) as X3
where id='<some_id>'
),
sub_x4 as
(
select
A.id, X4.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/yet_other_node/y_a_c_n/yet_another_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"yet_other_cd" varchar(50) PATH '@id'
-- and other cols --
) as X4
where id='<some_id>'
),
sub_x5 as
(
select
A.id, X5.*
from tbl_with_blob a,
XMLTABLE('$XMLDATA//BusData/LOB1/Vehicle/yet_other_node/y_o_n/yet_another_child2' passing XML_COL_TEXT as "XMLDATA"
COLUMNS
"yet_other_cd2" varchar(50) PATH '@id'
-- and other cols --
) as X5
where id='<some_id>'
)
select
X1.<cols>,
X2.<cols>,
X3.<cols>,
X4.<cols>,
X5.<cols>,
from X1, X2, X3, X4, X5
where
X1.id=X2.id
and (X1.id=X3.id and X2.id=X3.id)
and (X1.id=X4.id and X2.id=X4.id and X3.id=X4.id)
and (X1.id=X5.id and X2.id=X5.id and X3.id=X5.id and X4.id=X5.id)
with ur;
这一直持续到 运行,并且每个单独的查询都提供了正确的结果集和唯一的行。 X1 给出 4 行,X2 给出 9,X3 给出 11,X4 给出 7,X5 给出 6。 这些子查询中的每一个都包含 XML XPath,它们在其直接父节点中重复出现 - 多次。
但作为一个整体查询给出了这些的叉积 - 16632 行。 显然我在 JOIN 条件中遗漏了一些东西?
谢谢 LNC