从 SQL 服务器或 powerBuilder 中的主详细信息行创建 XML
Create XML from Master detail rows in SQL Server or powerBuilder
我有来自 SQL 服务器的主详细数据,如下所示,并希望按照以下格式生成 XML 以从 PowerBuilder 作为 SOAP XML 发送。
CREATE TABLE dbo.Orders
(
OrderNo varchar(10) NOT NULL,
PakDesc varchar(50) NOT NULL
)
GO
INSERT INTO Orders values('11111','Test1' )
GO
CREATE TABLE dbo.Components
(
OrderNo varchar(10) NOT NULL,
CompNo varchar(10) NOT NULL,
CompDesc varchar(50) NOT NULL,
Qty int NOT NULL
)
GO
INSERT INTO Components values('11111','01234', 'Comp1', 10 )
INSERT INTO Components values('11111','56789', 'Comp2', 5 )
GO
期望的XML输出
<entrylist>
<name>OrderNo</name>
<value>11111</value>
</entrylist>
<entrylist>
<name>PakDesc</name>
<value>Test1</value>
</entrylist>
<entrylist>
<name>CompNo1</name>
<value>01234</value>
</entrylist>
<entrylist>
<name>CompDesc1</name>
<value>Comp1</value>
</entrylist>
<entrylist>
<name>Qty1</name>
<value>10</value>
</entrylist>
<entrylist>
<name>CompNo2</name>
<value>56789</value>
</entrylist>
<entrylist>
<name>CompDesc2</name>
<value>Comp2</value>
</entrylist>
<entrylist>
<name>Qty2</name>
<value>5</value>
</entrylist>
在 PowerBuilder 中,我在 Datawindow 中获取这些数据,我可以导航每一行和每一列,并使用 CREATE PBDOM_Element 创建一个 XML 元素。
但我想知道是否有任何其他方法可以轻松生成类似的 XML?
可以像这样在 SQL 服务器中生成输出吗?
这是一个基于 XQuery FLWOR 表达式的解决方案。
它是一个 T-SQL 语句中的两步过程。
首先,为了模拟 master/details 结构,我们创建了一个原始的 XML,它将主数据作为属性,将详细信息作为元素。其次,我们通过 FLWOR 表达式塑造最终输出 XML。
SQL
-- DDL and sample data population, start
DECLARE @Orders TABLE (OrderNo varchar(10) NOT NULL, PakDesc varchar(50) NOT NULL);
INSERT INTO @Orders values('11111','Test1' );
DECLARE @Components TABLE
(
ID INT IDENTITY(1,1) PRIMARY KEY,
OrderNo varchar(10) NOT NULL,
CompNo varchar(10) NOT NULL,
CompDesc varchar(50) NOT NULL,
Qty int NOT NULL
);
INSERT INTO @Components VALUES
('11111','01234', 'Comp1', 10 )
,('11111','56789', 'Comp2', 5 );
-- DDL and sample data population, end
SELECT
(
SELECT o.OrderNo AS [@OrderNo], o.PakDesc AS [@PakDesc]
--, c.ID AS [@ID]
, ROW_NUMBER() OVER(ORDER BY o.OrderNo) AS [@ID]
, c.CompNo, c.CompDesc, c.Qty
FROM @Orders AS o LEFT OUTER JOIN
@Components AS c ON c.OrderNo = o.OrderNo
FOR XML PATH('r'), TYPE, ROOT('root')
).query('
for $y in /root/r (: master level :)
let $index := $y/@ID
return (if ($index eq 1) then
(
for $z in $y/@*[local-name(.) ne "ID"] (: all attributes except @ID :)
return <entrylist>
<name>{local-name($z)}</name>
<value>{data($z)}</value>
</entrylist>
)
else ()
,
for $x in $y/* (: details level :)
return <entrylist>
<name>{concat(local-name($x), $index)}</name>
<value>{data($x)}</value>
</entrylist>)
');
Output
<entrylist>
<name>OrderNo</name>
<value>11111</value>
</entrylist>
<entrylist>
<name>PakDesc</name>
<value>Test1</value>
</entrylist>
<entrylist>
<name>CompNo1</name>
<value>01234</value>
</entrylist>
<entrylist>
<name>CompDesc1</name>
<value>Comp1</value>
</entrylist>
<entrylist>
<name>Qty1</name>
<value>10</value>
</entrylist>
<entrylist>
<name>CompNo2</name>
<value>56789</value>
</entrylist>
<entrylist>
<name>CompDesc2</name>
<value>Comp2</value>
</entrylist>
<entrylist>
<name>Qty2</name>
<value>5</value>
</entrylist>
我有来自 SQL 服务器的主详细数据,如下所示,并希望按照以下格式生成 XML 以从 PowerBuilder 作为 SOAP XML 发送。
CREATE TABLE dbo.Orders
(
OrderNo varchar(10) NOT NULL,
PakDesc varchar(50) NOT NULL
)
GO
INSERT INTO Orders values('11111','Test1' )
GO
CREATE TABLE dbo.Components
(
OrderNo varchar(10) NOT NULL,
CompNo varchar(10) NOT NULL,
CompDesc varchar(50) NOT NULL,
Qty int NOT NULL
)
GO
INSERT INTO Components values('11111','01234', 'Comp1', 10 )
INSERT INTO Components values('11111','56789', 'Comp2', 5 )
GO
期望的XML输出
<entrylist>
<name>OrderNo</name>
<value>11111</value>
</entrylist>
<entrylist>
<name>PakDesc</name>
<value>Test1</value>
</entrylist>
<entrylist>
<name>CompNo1</name>
<value>01234</value>
</entrylist>
<entrylist>
<name>CompDesc1</name>
<value>Comp1</value>
</entrylist>
<entrylist>
<name>Qty1</name>
<value>10</value>
</entrylist>
<entrylist>
<name>CompNo2</name>
<value>56789</value>
</entrylist>
<entrylist>
<name>CompDesc2</name>
<value>Comp2</value>
</entrylist>
<entrylist>
<name>Qty2</name>
<value>5</value>
</entrylist>
在 PowerBuilder 中,我在 Datawindow 中获取这些数据,我可以导航每一行和每一列,并使用 CREATE PBDOM_Element 创建一个 XML 元素。
但我想知道是否有任何其他方法可以轻松生成类似的 XML? 可以像这样在 SQL 服务器中生成输出吗?
这是一个基于 XQuery FLWOR 表达式的解决方案。
它是一个 T-SQL 语句中的两步过程。
首先,为了模拟 master/details 结构,我们创建了一个原始的 XML,它将主数据作为属性,将详细信息作为元素。其次,我们通过 FLWOR 表达式塑造最终输出 XML。
SQL
-- DDL and sample data population, start
DECLARE @Orders TABLE (OrderNo varchar(10) NOT NULL, PakDesc varchar(50) NOT NULL);
INSERT INTO @Orders values('11111','Test1' );
DECLARE @Components TABLE
(
ID INT IDENTITY(1,1) PRIMARY KEY,
OrderNo varchar(10) NOT NULL,
CompNo varchar(10) NOT NULL,
CompDesc varchar(50) NOT NULL,
Qty int NOT NULL
);
INSERT INTO @Components VALUES
('11111','01234', 'Comp1', 10 )
,('11111','56789', 'Comp2', 5 );
-- DDL and sample data population, end
SELECT
(
SELECT o.OrderNo AS [@OrderNo], o.PakDesc AS [@PakDesc]
--, c.ID AS [@ID]
, ROW_NUMBER() OVER(ORDER BY o.OrderNo) AS [@ID]
, c.CompNo, c.CompDesc, c.Qty
FROM @Orders AS o LEFT OUTER JOIN
@Components AS c ON c.OrderNo = o.OrderNo
FOR XML PATH('r'), TYPE, ROOT('root')
).query('
for $y in /root/r (: master level :)
let $index := $y/@ID
return (if ($index eq 1) then
(
for $z in $y/@*[local-name(.) ne "ID"] (: all attributes except @ID :)
return <entrylist>
<name>{local-name($z)}</name>
<value>{data($z)}</value>
</entrylist>
)
else ()
,
for $x in $y/* (: details level :)
return <entrylist>
<name>{concat(local-name($x), $index)}</name>
<value>{data($x)}</value>
</entrylist>)
');
Output
<entrylist>
<name>OrderNo</name>
<value>11111</value>
</entrylist>
<entrylist>
<name>PakDesc</name>
<value>Test1</value>
</entrylist>
<entrylist>
<name>CompNo1</name>
<value>01234</value>
</entrylist>
<entrylist>
<name>CompDesc1</name>
<value>Comp1</value>
</entrylist>
<entrylist>
<name>Qty1</name>
<value>10</value>
</entrylist>
<entrylist>
<name>CompNo2</name>
<value>56789</value>
</entrylist>
<entrylist>
<name>CompDesc2</name>
<value>Comp2</value>
</entrylist>
<entrylist>
<name>Qty2</name>
<value>5</value>
</entrylist>