我有两个这样的xml文件:
<?xml version="1.0"?>
<instance xmlns="http://www.ubrea.com/xforms/88668970-6edb-0131-28e9-22000a1cda92" xmlns:tm="http://www.ubrea.com/xforms" >
<inputs>
<Truck_Number_Non_Barcode>MNKSJJHDHH88728</Truck_Number_Non_Barcode>
<VIN>
<Non_Barcode>xyz</Non_Barcode>
<ODO>1425788</ODO>
<Defect>
<Code>33J</Code>
</Defect>
</VIN>
</inputs>
</instance>
并且
<?xml version="1.0"?>
<instance xmlns="http://www.ubrea.com/xforms/88668970-6edb-0131-28e9-22000a1cda92" xmlns:tm="http://www.ubrea.com/xforms" >
<inputs>
<Number_Non_Barcode>mnbcdsddsd3455</Number_Non_Barcode>
<VIN>
<Non_Barcode>xyz</Non_Barcode>
<ODO>1425788</ODO>
</VIN>
</inputs>
</instance>
下面是我的用于解析xml文件的sqlquery:
declare @xmldata xml
set @xmldata ='
<?xml version="1.0"?>
<instance xmlns="http://www.ubrea.com/xforms/88668970-6edb-0131-28e9-22000a1cda92" xmlns:tm="http://www.ubrea.com/xforms" >
<inputs>
<Number_Non_Barcode>mnbcdsddsd3455</Number_Non_Barcode>
<VIN>
<Non_Barcode>xyz</Non_Barcode>
<ODO>1425788</ODO>
</VIN>
</inputs>
</instance>'
declare @sql nvarchar(max)
declare @xmlns varchar(max)
set @xmlns=''''+SUBSTRING(cast(@xmldata as varchar(max)),CHARINDEX('http://www.ubrea.com/xforms/',cast(@xmldata as varchar(max)),1),CHARINDEX('" xmlns:dm',cast(@xmldata as varchar(max)),1)-18)+''''
set @sql='
declare @xmldata xml
set @xmldata = '''+cast(@xmldata as varchar(max))+'''
begin try
;WITH XMLNAMESPACES
(
DEFAULT ' + @xmlns +
','+'''http://www.ubrea.com/xforms''' + ' as fm
)
select
Number_Non_Barcode, Non_Barcode, ODO, Code
from (
select
x.c.value(''(../../Number_Non_Barcode)[1]'', ''varchar(100)'') as Number_Non_Barcode,
x.c.value(''(../Non_Barcode)[1]'', ''varchar(100)'') as Non_Barcode,
x.c.value(''(../ODO)[1]'', ''varchar(100)'') as ODO,
x.c.value(''(Code)[1]'', ''varchar(100)'') as Code
from @xmldata.nodes(''/instance/inputs/VIN/Defect'') x(c)
) x
end try
begin catch
select ERROR_NUMBER() Code, ERROR_MESSAGE() Message
end catch'
exec sp_executesql @sql;
如果<Defect>
不可用且如果结果如此,如何进行查询:
Number_Non_Barcode Non_Barcode ODO Defect_Code
mnbcdsddsd3455 xyz 1425788 NULL
我不熟悉xml查询,似乎无法找到如何执行此操作的示例。任何帮助,将不胜感激。感谢
答案 0 :(得分:0)
我猜您的动态查询是存在的,因为您不知道默认命名空间。相反,您可以使用*
在XQuery中指定命名空间。
通过在几个步骤中使用..
和nodes()
粉碎XML,可以避免使用父轴cross apply
。由于Defect
节点可能丢失,因此在粉碎这些节点时必须使用outer apply
。
select I.X.value('(*:Number_Non_Barcode/text())[1]', 'varchar(100)') as Number_Non_Barcode,
V.X.value('(*:Non_Barcode/text())[1]', 'varchar(100)') as Non_Barcode,
V.X.value('(*:ODO/text())[1]', 'varchar(100)') as ODO,
D.X.value('(*:Code/text())[1]', 'varchar(100)') as Code
from @XMLData.nodes('/*:instance/*:inputs') as I(X)
cross apply I.X.nodes('*:VIN') as V(X)
outer apply V.X.nodes('*:Defect') as D(X)