Jimm Chen
Jimm Chen

Reputation: 3797

XSLT, how to sort by element name

I'm a newbie in XSLT. I just come up with a question and hope someone can help.

Assume I have a source xml,

<?xml version="1.0"?>
<docroot>
    <vc6>foo</vc6>
    <vc7>bar7</vc7>
    <vc8 arch="x64">amd64demo</vc8>
    <vc7>foo7</vc7>
    <vc6>bar</vc6>
</docroot> 

I'd like to turn it into:

<?xml version="1.0"?>
<docroot>
    <vc6>bar</vc6>
    <vc6>foo</vc6>
    <vc7>bar7</vc7>
    <vc7>foo7</vc7>
    <vc8 arch="x64">amd64demo</vc8>
</docroot> 

that is,

  1. child elements of should be sorted by element name, so <vc6> comes before <vc7> .
  2. If two children have the same element name, they should be sorted by their text value, so 'bar' is ahead of 'foo'.

How to write the xsl? Thank you.

Upvotes: 2

Views: 2273

Answers (2)

Michael Kay
Michael Kay

Reputation: 163595

Revision of legoscia's answer:

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

Upvotes: 5

legoscia
legoscia

Reputation: 41648

There are some examples of how to use xsl:sort in this answer. Something like this should work for you:

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

Upvotes: 4

Related Questions