复制所有XML元素并在XSL中更新其中一个元素

时间:2016-02-03 11:46:24

标签: xslt

我的项目中有一个要求是这样的, 我必须复制xml中的所有元素,如果存在,我必须更新少数元素,否则我必须添加它。

例如,在下面的xml中,我有一个元素Extrensic name" taxIncluded"> ,在翻译的xml中,我想要更新它的值。如果它丢失了,我必须包含它。

输入xml 1

<?xml version="1.0" encoding="UTF-8"?>
<InvoiceHeader>
    <Item1>
    Item description
    </Item1>

    <Extrensic name="taxIncluded">
        <percentage>
     10%
        </percentage>
    </Extrensic>
</InvoiceHeader>

输出

<?xml version="1.0" encoding="UTF-8"?>
<InvoiceHeader>
    <Item1>
    Item description
    </Item1>

    <Extrensic name="taxIncluded">
        <percentage>
     20%
        </percentage>
    </Extrensic>
</InvoiceHeader>

输入xml 2

<?xml version="1.0" encoding="UTF-8"?>
<InvoiceHeader>
    <Item1>
    Item description
    </Item1>
</InvoiceHeader>

输出

<?xml version="1.0" encoding="UTF-8"?>
<InvoiceHeader>
    <Item1>
    Item description
    </Item1>

    <Extrensic name="taxIncluded">
        <percentage>
     20%
        </percentage>
    </Extrensic>
</InvoiceHeader>

我尝试创建xsl但它没有按预期工作,我想在这里包含它但是它是一个非常大的xsl,在上面的xml示例中我只添加了它的一部分。

有人可以帮我怎么做?

1 个答案:

答案 0 :(得分:1)

以下是使用XSLT 2.0的两种方法...

方法1:

<xsl:transform
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    version="2.0">

<xsl:output omit-xml-declaration="yes" encoding="UTF-8" indent="yes" />
<xsl:strip-space elements="*" />
<xsl:param name="taxIncluded" select="20" />

<xsl:template match="@*|node()">
  <xsl:copy>
    <xsl:apply-templates select="@*|node()"/>
  </xsl:copy>
</xsl:template>

<xsl:template match="InvoiceHeader[not( Extrensic[@name='taxIncluded'])]">
  <xsl:copy>
    <xsl:apply-templates select="@*|node()"/>
    <Extrensic name="taxIncluded">
        <percentage>
          <xsl:value-of select="$taxIncluded" />%
        </percentage>
    </Extrensic>
  </xsl:copy>
</xsl:template>

<xsl:template match="Extrensic[@name='taxIncluded']/percentage">
  <xsl:copy>
     <xsl:value-of select="$taxIncluded" />%
  </xsl:copy>
</xsl:template>

</xsl:transform>

方法2:

<xsl:transform
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
    version="2.0">

<xsl:output omit-xml-declaration="yes" encoding="UTF-8" indent="yes" />
<xsl:strip-space elements="*" />
<xsl:param name="taxIncluded" select="20" />

<xsl:template match="@*|node()">
  <xsl:copy>
    <xsl:apply-templates select="@*|node()"/>
  </xsl:copy>
</xsl:template>

<xsl:template match="InvoiceHeader">
  <xsl:copy>
    <xsl:apply-templates select="@*|node()"/>
    <xsl:variable name="Ex" as="element(Extrensic)?">
      <xsl:if test="not( Extrensic[@name='taxIncluded'])">
        <Extrensic name="taxIncluded" />
      </xsl:if>
    </xsl:variable>
    <xsl:apply-templates select="$Ex" />
  </xsl:copy>
</xsl:template>

<xsl:template match="Extrensic[@name='taxIncluded']">
  <xsl:copy>
    <xsl:apply-templates select="@*"/>
    <percentage>
      <xsl:value-of select="$taxIncluded" />%
    </percentage>
  </xsl:copy>
</xsl:template>

</xsl:transform>