SQL Server:是否可以更改复杂XML元素的值?

时间:2016-04-28 12:57:18

标签: sql-server xml tsql xquery-sql

我需要更改XML元素中的值 - 对于这个无类型的版本,它以这种方式工作:

declare @X xml=
'<translations>
  <value lang="en-US">example</value>
  <value lang="de-DE">Beispiel</value>
</translations>';

set @X.modify('replace value of (/translations/value[@lang="en-US"]/text())[1] with "replacedValue"');

select @X.value('(/translations/value[@lang="en-US"])[1]','varchar(max)');

选择返回&#34;被替换的值&#34;为了&#34;价值&#34;具有属性lang =&#34; en-US&#34;。

的元素

不幸的是,我必须为数据库中的XML属性执行此操作,该数据库的类型为以下XML架构:

CREATE XML SCHEMA COLLECTION [dbo].[LocaleSchema] AS N'<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema"><xsd:element name="translations"><xsd:complexType><xsd:complexContent><xsd:restriction base="xsd:anyType"><xsd:sequence minOccurs="0" maxOccurs="unbounded"><xsd:element name="value"><xsd:complexType><xsd:simpleContent><xsd:extension base="xsd:string"><xsd:attribute name="lang" type="language" /></xsd:extension></xsd:simpleContent></xsd:complexType></xsd:element></xsd:sequence></xsd:restriction></xsd:complexContent></xsd:complexType></xsd:element><xsd:simpleType name="language"><xsd:restriction base="xsd:string"><xsd:enumeration value="de-DE" /><xsd:enumeration value="en-US" /></xsd:restriction></xsd:simpleType></xsd:schema>'

为了更好的可读性,之后只有非常简单的XML模式:

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema">
    <xsd:element name="translations">
        <xsd:complexType>
            <xsd:complexContent>
                <xsd:restriction base="xsd:anyType">
                    <xsd:sequence minOccurs="0" maxOccurs="unbounded">
                        <xsd:element name="value">
                            <xsd:complexType>
                                <xsd:simpleContent>
                                    <xsd:extension base="xsd:string">
                                        <xsd:attribute name="lang" type="language" />
                                    </xsd:extension>
                                </xsd:simpleContent>
                            </xsd:complexType>
                        </xsd:element>
                    </xsd:sequence>
                </xsd:restriction>
            </xsd:complexContent>
        </xsd:complexType>
    </xsd:element>
    <xsd:simpleType name="language">
        <xsd:restriction base="xsd:string">
            <xsd:enumeration value="de-DE" />
            <xsd:enumeration value="en-US" />
        </xsd:restriction>
    </xsd:simpleType>
</xsd:schema>

正如你在这里看到的那样&#34;值&#34; XML元素是复杂类型。根据文档,modify()函数仅对简单类型有效。 (此外,text()函数仅对简单类型有效)

之后是来自上面的类型内容的SQL语句 - 在尝试修改时会导致错误:

declare @X xml (CONTENT [dbo].[LocaleSchema])=
'<translations>
  <value lang="en-US">example</value>
  <value lang="de-DE">Beispiel</value>
</translations>';

set @X.modify('replace value of (/translations/value[@lang="en-US"]/text())[1] with "replacedValue"');

有建议可以解决吗?或者更改XML属性的任何其他可能性? (当然,我需要在现实生活中的UPDATE语句中使用它)

提前谢谢!

1 个答案:

答案 0 :(得分:1)

这有效......

CREATE XML SCHEMA COLLECTION [dbo].[LocaleSchema] AS N'<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema"><xsd:element name="translations"><xsd:complexType><xsd:complexContent><xsd:restriction base="xsd:anyType"><xsd:sequence minOccurs="0" maxOccurs="unbounded"><xsd:element name="value"><xsd:complexType><xsd:simpleContent><xsd:extension base="xsd:string"><xsd:attribute name="lang" type="language" /></xsd:extension></xsd:simpleContent></xsd:complexType></xsd:element></xsd:sequence></xsd:restriction></xsd:complexContent></xsd:complexType></xsd:element><xsd:simpleType name="language"><xsd:restriction base="xsd:string"><xsd:enumeration value="de-DE" /><xsd:enumeration value="en-US" /></xsd:restriction></xsd:simpleType></xsd:schema>';
GO

declare @X xml (CONTENT [dbo].[LocaleSchema])=
'<translations>
  <value lang="en-US">example</value>
  <value lang="de-DE">Beispiel</value>
</translations>';

set @X.modify('replace value of (/translations/value[@lang="en-US"])[1] with "replacedValue"');

SELECT @x;
GO

--clean up
--DROP XML SCHEMA COLLECTION dbo.LocaleSchema;