使用XSLT将XML单个元素转换为XML属性,并将其作为元素保存在输出中

时间:2015-02-17 00:50:27

标签: xml xslt

我们有一个当前系统输出XML文件,格式如下:

<ResultSet rowCount="2">
    <Row>
     <Entry>83708</Entry>
     <mark>L24653338N1</mark>
     <Processed>NO</Processed>
    </Row>
    <Row>
     <Entry>99999</Entry>
     <mark>L24653338N1</mark>
     <Processed>YES</Processed>
    </Row>
</ResultSet>

我需要转变为:

<ResultSet rowCount="2">
    <Row Processed="NO">
     <Entry>83708</Entry>
     <mark>L24653338N1</mark>
     <Processed>NO</Processed>
    </Row>
    <Row Processed="YES">
     <Entry>99999</Entry>
     <mark>L24653338N1</mark>
     <Processed>YES</Processed>
    </Row>
</ResultSet>

有人知道如何使用.XSL完成此操作吗?

这就是我所做的:

</xsl:template>
    <xsl:template name="transform">
        <Row>
        <xsl:if test="$linecount&gt;0">
            <xsl:for-each       select="/Msg/Body/Payload[./@Role='S']/Msg/Body/Payload[./@sql]/SqlResult/ResultSet/Row">
                <xsl:attribute name="pos"><xsl:value-of select="position()"/></xsl:attribute>
                <Entry>
                    <xsl:value-of select="./Entry"/>
                </Entry>
                <mark>
                    <xsl:value-of select="./mark"/>
                </mark>
                <Proccessed>
                    <xsl:value-of select="./Proccessed"/>
                </Proccessed>
            </xsl:for-each>
        </xsl:if>
    </Row>
</xsl:template>

1 个答案:

答案 0 :(得分:1)

在诸如此类的任务中,您只需要更改为部分XML,通常的方法是从Identity Transform开始

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

它本身将按原样复制所有节点和属性,因此您只需要为要更改的内容编写模板。在您的情况下,您要在Processed元素上添加新的Row属性。这意味着您只需要一个与Row元素匹配的模板,然后添加此属性,如此

<xsl:template match="Row">
    <Row Processed="{Processed}">
        <xsl:apply-templates select="@*|node()"/>
    </Row>
</xsl:template>

请注意在您正在创建的属性中使用Attribute Value Templates。花括号{}表示要被计算的表达式,而不是字面输出,因此属性的值实际上是Processed元素的值。

试试这个XSLT

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

    <xsl:template match="Row">
        <Row Processed="{Processed}">
            <xsl:apply-templates select="@*|node()"/>
        </Row>
    </xsl:template>

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

请注意,您还可以使用xsl:attribute调用创建属性。例如

<xsl:template match="Row">
    <Row>
        <xsl:attribute name="Processed">
            <xsl:value-of select="Processed" />
        </xsl:attribute>
        <xsl:apply-templates select="@*|node()"/>
    </Row>
</xsl:template>

但正如您所看到的,这更详细,因此在可能的情况下首选属性值模板。