使用T-SQL从XML中提取子节点值

时间:2013-09-11 09:31:58

标签: sql sql-server xml tsql

我一直试图从Microsoft Lync数据库通过T-SQL返回的信封中获取'availability'节点的值。通常使用.value('(/ MyElement / Something)[1]')的方法似乎不适合我。

<state xsi:type="aggregateState" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://schemas.microsoft.com/2006/09/sip/state">
<availability>3500
</availability>
<delimiter xmlns="http://schemas.microsoft.com/2006/09/sip/commontypes" />
<timeZoneBias>-60
</timeZoneBias>
<timeZoneName>GMT Daylight Time
</timeZoneName>
<timeZoneAbbreviation>GMT Daylight Time
</timeZoneAbbreviation>
<device>computer
</device>
<end xmlns="http://schemas.microsoft.com/2006/09/sip/commontypes" />
</state>

这是我一直在尝试的查询:

SELECT TOP 1 
    CAST(SUBSTRING(i.Data, 0, 4000) as XML).value('(/state//availability)[1]', 'varchar(256)')
FROM dbo.PublishedCategoryInstanceView AS i
INNER JOIN dbo.CategoryDef AS d
    ON (d.CategoryId = i.CategoryId)
WHERE i.PublisherId = (SELECT ResourceId FROM dbo.Resource
                        WHERE UserAtHost = 'my.email@mydomain.local')
ORDER BY i.LastPubTime DESC

除非我CAST(SUBSTRING(i.Data, 0, 4000) as XML).value('(/)[1]', 'varchar(256)')返回3500-60GMT Daylight TimeGMT Daylight Timecomputer

,否则我回来的都是'空'

我知道当我删除state元素上的三个属性时,我可以对数据执行普通的XML查询,所以我可以通过使用一些替换语句来操作字符串来解决这个问题,但我宁愿知道究竟是什么如果有人可以提供帮助,我在这里做错了吗?

1 个答案:

答案 0 :(得分:3)

您只是简单地忽略 XML根节点上存在的XML命名空间:

<state xsi:type="aggregateState" 
       xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"   
       xmlns="http://schemas.microsoft.com/2006/09/sip/state">
       ******************************************************      

您需要在T-SQL查询中包含它!

尝试这样的事情:

;WITH XMLNAMESPACES(DEFAULT 'http://schemas.microsoft.com/2006/09/sip/state')
SELECT TOP 1 
    CAST(SUBSTRING(i.Data, 0, 4000) as XML).value('(/state//availability)[1]', 'varchar(256)')
FROM 
    dbo.PublishedCategoryInstanceView AS i
相关问题