tags:

views:

116

answers:

1

Hello, I need to have my XSLT stylesheet sort my XML file's child nodes, but only certain ones. Here's an example of what the XML is like:

<?xml version="1.0"?>
<xmltop>
<child1 num="1">
<data>12345</data>
</child1>

<child1 num="2">
<data>12345</data>
</child1>

<child2 num="3">
<data>12345</data>
</child2>

<child2 num="2">
<data>12345</data>
</child2>

<child2 num="1">
<data>12345</data>
</child2>
</xmltop>

And this is the XSL file I'm using:

<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform"&gt;

<xsl:template match="/xmltop">
 <xsl:copy>
  <xsl:apply-templates>
   <xsl:sort select="@num"/>
  </xsl:apply-templates>
 </xsl:copy>
</xsl:template>
<xsl:template match="child2">
 <xsl:copy-of select="."/>
</xsl:template>

</xsl:stylesheet>

This creates problems for me because the nodes are stripped of their tags, and their contents remain, making my XML invalid. I'm not really an expert at XSL so pardon me if this is a dumb question.

The <child2>'s are sorted properly.

Thank you.

+1  A: 

It is not defined what the output should be, so this is just me in "guess mode":

<xsl:stylesheet version="1.0"
    xmlns:xsl="http://www.w3.org/1999/XSL/Transform"&gt;
    <xsl:output omit-xml-declaration="yes" indent="yes"/>
    <xsl:strip-space elements="*"/>

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

 <xsl:template match="xmltop">
  <xsl:copy>
    <xsl:apply-templates>
      <xsl:sort select="(name() = 'child2')*@num"
       data-type="number"/>
    </xsl:apply-templates>
  </xsl:copy>
 </xsl:template>
</xsl:stylesheet>

When this transformation is applied on the provided XML document:

<xmltop>
    <child1 num="1">
        <data>12345</data>
    </child1>
    <child1 num="2">
        <data>12345</data>
    </child1>
    <child2 num="3">
        <data>12345</data>
    </child2>
    <child2 num="2">
        <data>12345</data>
    </child2>
    <child2 num="1">
        <data>12345</data>
    </child2>
</xmltop>

the (what I think is) wanted result is produced:

<xmltop>
   <child1 num="1">
      <data>12345</data>
   </child1>
   <child1 num="2">
      <data>12345</data>
   </child1>
   <child2 num="1">
      <data>12345</data>
   </child2>
   <child2 num="2">
      <data>12345</data>
   </child2>
   <child2 num="3">
      <data>12345</data>
   </child2>
</xmltop>
Dimitre Novatchev
thank you, exactly what I wanted! The output I needed was identical to the input except with the nodes sorted in order as this stylesheet does.
MT