如何根据元素值返回 XML 节点序号,或删除节点?

JNK*_*JNK 4 xml sql-server-2008-r2 xquery

我有一个与此类似的 XML 文档:

<Root>
  <Sub>
    <Record>
      <Guid>aslkjflaksjflkasjfkljsd</Guid>
    </Record>
    <Record>
       <Guid>opqiwuerl;kasdlfkjawop</Guid>
    </Record>
  </Sub>
</Root>
Run Code Online (Sandbox Code Playgroud)

我正在<Record>根据某些标准替换整个节点。该<Record>节点包含一个<Guid>,我可以用它来识别它们(那些假装是有效的GUID请!)。

知道了 GUID,我将该节点的 XML 返回到一个变量中以供进一步处理。在下游,我需要能够删除该特定节点,以便我可以insert将节点的修改版本恢复到原始文档中。

有没有办法确定序数,或者使用delete/replace方法根据元素的值删除节点的另一种方法?

Mik*_*son 5

如果变量中有值,则可以在谓词中使用sql:variable()进行删除。

declare @XML xml = '
<Root>
  <Sub>
    <Record>
      <Guid>aslkjflaksjflkasjfkljsd</Guid>
    </Record>
    <Record>
       <Guid>opqiwuerl;kasdlfkjawop</Guid>
    </Record>
  </Sub>
</Root>'

declare @Guid varchar(30) = 'aslkjflaksjflkasjfkljsd'

set @XML.modify('delete /Root/Sub/Record[Guid = sql:variable("@Guid")]')
Run Code Online (Sandbox Code Playgroud)

用新记录替换记录看起来像这样。

declare @XML xml = '
<Root>
  <Sub>
    <Record>
      <Guid>aslkjflaksjflkasjfkljsd</Guid>
      <Value>some value</Value>
    </Record>
    <Record>
       <Guid>opqiwuerl;kasdlfkjawop</Guid>
    </Record>
  </Sub>
</Root>'

declare @Guid varchar(30) = 'aslkjflaksjflkasjfkljsd'
declare @NewRecord xml = '
<Record>
  <Guid>aslkjflaksjflkasjfkljsd</Guid>
  <Value>some new value</Value>
</Record>'

set @XML.modify('insert sql:variable("@NewRecord") after (/Root/Sub/Record[Guid = sql:variable("@Guid")])[1]')
set @XML.modify('delete (/Root/Sub/Record[Guid = sql:variable("@Guid")])[1]')
Run Code Online (Sandbox Code Playgroud)

首先在现有记录之后添加新记录,并删除 Guid 匹配的第一个匹配项。如果没有[1]在删除中,您将删除所有事件,而不仅仅是第一个。