我有一个SQL Server XML列,其中包含以下数据:
<History>
<Entry>
.....
</Entry>
<Entry>
.....
</Entry>
</History>
我需要为每个Entry元素添加一个唯一标识符,得到以下结果:
<History>
<Entry entryID="AAA">
.....
</Entry>
<Entry entryID="BBB">
.....
</Entry>
</History>
我让它适用于Entry元素的第一次出现,但不知道如何将其应用于所有出现的元素。另外,这个entryID是一个GUID,我不知道如何为每一行生成一个新的ID。
这是我更新第一个元素的方式。
declare @eventId varchar(64)
set @eventId = CONVERT(varchar(64),NEWID())
update Histories
set XmlHistory.modify('
insert attribute EntryID {sql:variable("@eventId")}
into (History/Entry)[1]
')
where HistoryID=285162
我也有查询,该查询选择需要此属性的元素并且尚不具有此属性。这给出了主键和我需要更新的元素。我无法获得用于元素数组索引的唯一元素标识符。
select h.id rowPK, m.c.query('.') theElement
from TheTable h
cross apply h.XMLColumn.nodes('History/Entry[not(@EntryID)]') m(c)
where XMLColumn.exist('(History/Entry)')= 1
答案 0 :(得分:0)
在SQL Server中操作XML可能非常困难,如果可以的话,可以选择其他任何选项!您应在将其作为XML加载到Sql Server之前应用唯一的ID。我能做的最好的事情是将XML切碎成表变量,添加键,然后将其提取为XML流。希望对您有帮助...
请注意,这确实会检查重复的键,因此您将需要处理重复的键,并且需要包括问题中未引用的所有其他节点或元素。
declare @Histories table
(
HistoryID int,
XmlHistory xml
)
insert into @Histories values (285162, '
<History>
<Entry>
Entry 1
</Entry>
<Entry>
Entry 2
</Entry>
<Entry>
Entry 3
</Entry>
<Entry>
Entry 4
</Entry>
</History>');
declare @tmp table
(
EntryVal varchar(max),
EntryGuid varchar(64)
)
insert into @tmp(EntryVal, EntryGuid)
SELECT p1.value(N'.[1]','nvarchar(max)') AS EntryValue, CONVERT(varchar(64),NEWID())
from @Histories H1
outer apply H1.XmlHistory.nodes(N'/History/Entry') AS A(p1)
select EntryGuid as '@ID', EntryVal as "data()"
from @tmp
for XML PATH ('ENTRY'), root ('HISTORY');
输出应如下所示
<HISTORY>
<ENTRY ID="1C5C9492-36C8-4E4E-9AE3-DF7E2F1C1948">
Entry 1
</ENTRY>
<ENTRY ID="9AC4BB5D-C471-4C89-947B-8C17D2BD446C">
Entry 2
</ENTRY>
<ENTRY ID="10A81C91-A58B-4846-A857-A14BFB7F9CB7">
Entry 3
</ENTRY>
<ENTRY ID="0E65D134-37A2-489C-8C72-5BE52D08D7B1">
Entry 4
</ENTRY>
</HISTORY>