简体   繁体   中英

How to move XML element and add a child element at the same time with XSLT?

What I'm trying to accomplish here is move an element (including it child nodes), and then add a child node within that element, or vice versa. It seems that I can only do one thing at a time. Is possible to do both at the same time?

Here is my input xml

<?xml version="1.0" encoding="UTF-8"?>
<catalog>
    <box1>
        <cd1>
            <title>Title 1</title>
            <artist>Bob Dylan</artist>
            <year>1985</year>
        </cd1>
        <cd2>
            <title>Title 2</title>
            <artist>Bonnie Tyler</artist>
            <year>1988</year>
        </cd2>
    </box1>
    <box2>
        <cd3>
            <title>Title 3</title>
            <artist>Metallica</artist>
        </cd3>
    </box2>
</catalog>

Would like to have the output like this

<catalog>
<box1>
    <cd1>
        <title>Title 1</title>
        <artist>Bob Dylan</artist>
        <year>1985</year>
    </cd1>
    <cd2>
        <title>Title 2</title>
        <artist>Bonnie Tyler</artist>
        <year>1988</year>
    </cd2>
    <cd3>
        <title>Title 3</title>
        <artist>Metallica</artist>
        <year>1990</year>
    </cd3>
</box1>

As you can see element cd3 moved and a child node of is added as well.

Here is what I did and all it does just moving the element regardless what order I put of the code.

<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="3.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="*"/>

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

    <!-- add a child element -->
    <xsl:template match="cd3">
        <xsl:copy>
            <xsl:apply-templates/>
            <year>1990</year>
        </xsl:copy>
    </xsl:template>

    <!-- move node -->
    <xsl:template match="/catalog">
        <xsl:copy>
                <xsl:apply-templates />
                <xsl:copy-of select="box2/cd3"/>
        </xsl:copy>
    </xsl:template>
    <xsl:template match="box2"/>

</xsl:stylesheet>

<xsl:copy-of select="box2/cd3"/>更改为<xsl:apply-templates select="box2/cd3"/> ,并将<xsl:template match="/catalog">更改为<xsl:template match="/catalog/box1">

I got it resolved by following code below. Thanks for the help got me started on further investigation.

<xsl:template match="/catalog">
    <xsl:copy>
        <box1>
            <xsl:apply-templates />
            <xsl:apply-templates select="box2/cd3"/>
        </box1>
    </xsl:copy>
</xsl:template>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM