我想有几个 AuditText 节点,其中一些属于 Blondie?
您可以分解完整的 XML,并使用类似表格的数据在经典的 WHERE 子句中使用 LIKE 过滤它。但更好的是XQuery。最好使用.nodes() 方法,但您也可以使用.query() 甚至.value()。
在这个例子中,我添加了一个根节点和几个测试节点:
DECLARE @xml XML=
'<root>
<AuditText Username="Blondie" CustomerGUID="xxxxxxxxxx3C4B35821FC0" IPAddress="xx.xxx.xxx.xx" />
<AuditText Username="Test1" CustomerGUID="xxxxxxxxxx11111111" IPAddress="xx.xxx.111.11" />
<AuditText Username="Blondie" CustomerGUID="xxxxxxxxxx3C4B35821FC0" IPAddress="xx.xxx.xxx.xx" />
<AuditText Username="Test2" CustomerGUID="xxxxxxxxxx222222222" IPAddress="xx.xxx.222.22" />
</root>
';
SELECT Blondie.value('@CustomerGUID','varchar(max)') AS CustomerGuid --you might set the type to "uniqueidentifier", if the value is a valid GUID
FROM @xml.nodes('/root/AuditText[@Username="Blondie"]') AS Only(Blondie);
--This is the way to insert your search string via variable
DECLARE @Username VARCHAR(100)='Test1';
SELECT MyUser.value('@CustomerGUID','varchar(max)')
FROM @xml.nodes('/root/AuditText[@Username=sql:variable("@Username")]') AS Only(MyUser);
如果您在 AuditTable 中搜索行,您可以使用 .exist():
CREATE TABLE #t_audit(ID INT IDENTITY,AuditData XML);
INSERT INTO #t_audit(AuditData) VALUES
('<AuditText Username="Blondie" CustomerGUID="xxxxxxxxxx3C4B35821FC0" IPAddress="xx.xxx.xxx.xx" />')
,('<AuditText Username="Blondie" CustomerGUID="xxxxxxxxxx3C4B35821FC0" IPAddress="xx.xxx.xxx.xx" />')
,('<AuditText Username="Test1" CustomerGUID="xxxxxxxxxx11111111" IPAddress="xx.xxx.111.11" />')
,('<AuditText Username="Blondie" CustomerGUID="xxxxxxxxxx3C4B35821FC0" IPAddress="xx.xxx.xxx.xx" />')
,('<AuditText Username="Test2" CustomerGUID="xxxxxxxxxx222222222" IPAddress="xx.xxx.222.22" />');
SELECT *
FROM #t_audit
WHERE AuditData.exist('AuditText[@Username="Blondie"]')=1;
--DROP TABLE #t_audit;
最后,如果您的 XML 格式不正确,您可以只使用过滤器
WHERE CAST(AuditData AS VARCHAR(MAX)) LIKE '%Blondie%'
或者(更准确一点)
WHERE CAST(AuditData AS VARCHAR(MAX)) LIKE '% Username="Blondie"%'