我需要将每日 XML 文件集成到我的系统中。
XML 文件的架构类似于:
create table txml(id int identity, data xml);
insert into txml (data) values ('
<order>
<trans DTrans="20170102" HTrans="10:52"></trans>
<head Id="552665566"></head>
<lin headId="552665566">
<dLin Id="00001" CoArt="1111111" CoArtCust="05220001" NameArt="Product1" dateVal="20161115" />
<acum DCalAcm="20170101" DIniAcm="20161115"><qtyAcm Qty="1101163.00" /></acum>
<lastOrd Id="95767" QtyLastOrd="12000.00" DLastOrd="20170101" />
<pLin LType="4"><uni Qty="24000.00"/><dIni Date="20170104"/><dEnd Date="20170108"/></pLin>
<pLin LType="4"><uni Qty="20000.00"/><dIni Date="20170109"/><dEnd Date="20170112"/></pLin>
<pLin LType="4"><uni Qty="24000.00"/><dIni Date="20170113"/><dEnd Date="20170116"/></pLin>
</lin>
<lin headId="552665566">
<dLin Id="00002" CoArt="2222222" CoArtCust="05269958" NameArt="Product2" dateVal="20161101" />
<acum DCalAcm="20170101" DIniAcm="20161101"><qtyAcm Qty="552652.00" /></acum>
<lastOrd Id="49956" QtyLastOrd="5000.00" DLastOrd="20170101" />
<pLin LType="4"><uni Qty="2200.00"/><dIni Date="20170104"/><dEnd Date="20170108"/></pLin>
<pLin LType="4"><uni Qty="3000.00"/><dIni Date="20170109"/><dEnd Date="20170116"/></pLin>
</lin>
</order>');
正如您所看到的,对于每个<lin>
部分,您都可以找到未知数量的<pLin>
行。到目前为止,我正在使用 C# 和 .Net 控制台应用程序完成这项工作,但我想使用 SQL 来完成这项工作。
到目前为止,我可以<lin>
使用下一个查询获得一组标签:
SELECT T2.lin.value('(./dLin/@Id)[1]', 'int') Id,
T2.lin.value('(./dLin/@CoArt)[1]', 'varchar(20)') CoArt,
T2.lin.value('(./dLin/@CoArtCust)[1]', 'varchar(20)') CoArtCust,
T2.lin.value('(./lastOrd/@Id)[1]', 'varchar(20)') lastOrderId,
T2.lin.value('(./lastOrd/@QtyLastOrd)[1]', 'decimal(18,2)') QtyLastOrd
FROM txml
CROSS APPLY data.nodes('/order/lin') as T2(lin);
这会产生下一个结果:
Id | CoArt | CoArtCust | lastOrderId | QtyLastOrd
-: | :------ | :-------- | :---------- | :---------
1 | 1111111 | 05220001 | 95767 | 12000.00
2 | 2222222 | 05269958 | 49956 | 5000.00
<pLin>
但我应该添加与标签对应的嵌套行并产生下一个结果:
Id | CoArt | CoArtCust | lastOrderId | QtyLastOrd | DIni | DEnd | NextQty
-: | :------ | :-------- | :---------- | :--------- | ---------- | ---------- | ---------
1 | 1111111 | 05220001 | 95767 | 12000.00 | 04/01/2017 | 08/01/2017 | 24000.00
1 | 1111111 | 05220001 | 95767 | 12000.00 | 09/01/2017 | 12/01/2017 | 20000.00
1 | 1111111 | 05220001 | 95767 | 12000.00 | 13/01/2017 | 16/01/2017 | 24000.00
2 | 2222222 | 05269958 | 49956 | 5000.00 | 04/01/2017 | 08/01/2017 | 2200.00
2 | 2222222 | 05269958 | 49956 | 5000.00 | 09/01/2017 | 16/01/2017 | 3000.00
我在这里设置了一个dbfiddle
您可以添加一个附加项
CROSS APPLY
以按您需要的方式拆分行:我不得不猜测 DINi 的数据类型,按要求正确。