我有一列ntext数据类型而非XML。它存储所有xml数据。我需要根据xml节点值获取记录。 =>输入值为CpsiaId = 456并且应该返回在xml中具有此值的所有记录
我尝试了select * from tableName
where convert(xml,column_name).value('data((/root/ProductInformation/CPSIA/CpsiaDetails/Item/CpsiaId)[1])','int') = 456
但它不起作用....获取基于xml节点值的记录的任何想法或其他方式。
示例Xml:
<root>
<ProductInformation>
<Name> Truck with Battery Charger</Name>
<Description>Fr.</Description>
<CPSIA>
<CpsiaDetails>
<Item>
<CpsiaId>456</CpsiaId>
<CpsiaMessage>waring</CpsiaMessage>
</Item>
<Item>
<CpsiaId>236</CpsiaId>
<CpsiaMessage>to health</CpsiaMessage>
</Item>
</CpsiaDetails>
</CPSIA>
</ProductInformation>
</root>
答案 0 :(得分:4)
convert(xml,column_name).exist('/root/ProductInformation/CPSIA/CpsiaDetails/Item[CpsiaId=456]') = 1
如果您需要动态值,则可以使用sql:variable()
替换常量(456
)(假设数字变量为@i
):
'/root/ProductInformation/CPSIA/CpsiaDetails/Item[CpsiaId=sql:variable("@i")]'
修改强>
请求的示例代码:
DECLARE @t nvarchar(MAX);
SET @t = '<root>
<ProductInformation>
<Name> Truck with Battery Charger</Name>
<Description>Fr.</Description>
<CPSIA>
<CpsiaDetails>
<Item>
<CpsiaId>456</CpsiaId>
<CpsiaMessage>waring</CpsiaMessage>
</Item>
<Item>
<CpsiaId>236</CpsiaId>
<CpsiaMessage>to health</CpsiaMessage>
</Item>
</CpsiaDetails>
</CPSIA>
</ProductInformation>
</root>'
DECLARE @i int;
SET @i = 456;
SELECT convert(xml,@t).exist('/root/ProductInformation/CPSIA/CpsiaDetails/Item[CpsiaId=sql:variable("@i")]')
答案 1 :(得分:0)
使用CTE首先将其转换为XML可能更容易,然后执行CROSS应用。这是一个样本
Declare @test table (id int identity, xmlData nvarchar(max))
Insert Into @test
(xmldata)
Values
('<root>
<ProductInformation>
<Name> Truck with Battery Charger</Name>
<Description>Fr.</Description>
<CPSIA>
<CpsiaDetails>
<Item>
<CpsiaId>456</CpsiaId>
<CpsiaMessage>waring</CpsiaMessage>
</Item>
<Item>
<CpsiaId>236</CpsiaId>
<CpsiaMessage>to health</CpsiaMessage>
</Item>
</CpsiaDetails>
</CPSIA>
</ProductInformation>
</root>'),
('<root>
<ProductInformation>
<Name> Truck with Battery Charger</Name>
<Description>Fr.</Description>
<CPSIA>
<CpsiaDetails>
<Item>
<CpsiaId>999</CpsiaId>
<CpsiaMessage>waring</CpsiaMessage>
</Item>
<Item>
<CpsiaId>123</CpsiaId>
<CpsiaMessage>to health</CpsiaMessage>
</Item>
</CpsiaDetails>
</CPSIA>
</ProductInformation>
</root>')
;with cte as (select id, convert(xml,t.xmlData) xdata from @test t )
SELECT t.*
from cte inner join @test t
on cte.id = t.id
cross apply cte.xdata.nodes('//root/ProductInformation/CPSIA/CpsiaDetails/Item') x(nd)
WHERE
x.nd.value('CpsiaId[1]','int') =456
使用Lucero对表的选择(而不是xml变量)的答案
DECLARE @i int;
SET @i = 456;
SELECT *
FROM
@test
WHERE
convert(xml,xmlData).exist('/root/ProductInformation/CPSIA/CpsiaDetails/Item[CpsiaId=sql:variable("@i")]') = 1