使用XSL将属性移动到子元素

时间:2017-07-21 07:49:56

标签: xml xslt

我遇到了无法解决的问题。这是我所拥有的xml结构的片段:

    <body>
        <tu creationdate="01022015" creationid="author1" changedate="02022015" changeid="author2">
            <tuv xml:lang="it-IT">
                <seg>Questo è testo</seg>
            </tuv>
            <tuv xml:lang="en-GB">
                <seg>This is a test</seg>
            </tuv>
            <tuv xml:lang="de-DE">
                <seg>Das ist ein Test</seg>
            </tuv>
        </tu>
        <tu>
        </tu>
    </body>
</tmx>

我希望将所有属性从元素移动到子元素而不覆盖任何内容。像这样:

    <body>
        <tu>
            <tuv xml:lang="it-IT" creationdate="01022015" creationid="author1" changedate="02022015" changeid="author2">
                <seg>Questo è testo</seg>
            </tuv>
            <tuv xml:lang="en-GB" creationdate="01022015" creationid="author1" changedate="02022015" changeid="author2">
                <seg>This is a test</seg>
            </tuv>
            <tuv xml:lang="de-DE" creationdate="01022015" creationid="author1" changedate="02022015" changeid="author2">
                <seg>Das ist ein Test</seg>
            </tuv>
        </tu>
        <tu>
        </tu>
    </body>
</tmx>

这是我迄今为止的最佳尝试:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:fo="http://www.w3.org/1999/XSL/Format">
    <xsl:output method="xml" indent="yes"/>

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

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

</xsl:stylesheet>

不幸的是,这总是会覆盖元素中的xml:lang属性。 有什么建议吗?

提前谢谢

恩里科

1 个答案:

答案 0 :(得分:0)

  

这总是会覆盖元素中的xml:lang属性。

它不会覆盖它。您只是没有在xsl:apply-templates说明中包含现有属性(尽管您确实包括node()两次,因此复制了所有子元素。)

此外,为了获得所需的结果,还必须从父tu元素中删除属性。

以这种方式尝试:

XSLT 1.0

<xsl:stylesheet version="1.0" 
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" version="1.0" encoding="UTF-8" indent="yes"/>
<xsl:strip-space elements="*"/>

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

<xsl:template match="tu/@*"/>

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

</xsl:stylesheet>

请注意使用xsl:copy-of添加属性。这是因为在我们添加了匹配它们的空模板后,使用xsl:apply-templates将无法执行任何操作。