user14503637
user14503637

Reputation:

How to grab all elements within parent tag and sort with XSLT?

Below is the XML document I am trying to format

<?xml version="1.0"?>
<?xml-stylesheet type="text/xsl" href="myXSLT_Q9.xsl"?> 
<orders> 
    <order> 
        <customerid>2384</customerid> 
        <status>pending</status> 
        <item instock="Y" itemid="SD93"> 
            <name>Flying By Roller Skates</name> 
            <price>25.00</price> 
            <qty>25</qty> 
        </item> 
        <item instock="N" itemid="B12"> 
            <name>Bounce-o Ball</name> 
            <price>.35</price> 
            <qty>150</qty> 
        </item> 
    </order> 
    <order> 
        <customerid>5268</customerid> 
        <status>complete</status> 
        <item instock="Y" itemid="Q52"> 
            <name>Crash N Burn Skis</name> 
            <price>20</price> 
            <qty>10</qty> 
        </item> 
    </order> 
    <order> 
        <customerid>3384</customerid> 
        <status>pending</status> 
        <item instock="Y" itemid="PS93"> 
            <name>All Star Shoe</name> 
            <price>55.00</price> 
            <qty>12</qty> 
        </item> 
        <item instock="Y" itemid="M12"> 
            <name>All Star Hat</name> 
            <price>44.35</price> 
            <qty>15</qty> 
        </item> 
    </order>
</orders> 

I am trying to loop through all the items and put the entire data for each item into a table but for some reason my code only grabs the Name, Price, and Qty tags under the Item tag and everything ive tried wont grab the Customerid and Status tag. Also the sort condition seems right but when i add it, it stops working.

<?xml version="1.0" encoding="UTF-8" ?>

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

   <xsl:template match="/">

      <html>
         <head>
            <title>Title of the page</title>
         </head>

         <body>
            <table>
            <xsl:for-each select="//item">
               <xsl:sort select="//item/@itemid">
               <xsl:if test="@instock = 'N'">
                  <tr style="background-color:yellow">             
                     <td><xsl:value-of select="customerid"/></td>
                     <td><xsl:value-of select="status"/></td>
                     <td><xsl:value-of select="name"/></td>
                     <td><xsl:value-of select="price"/></td>
                     <td><xsl:value-of select="qty"/></td>
                  </tr>
               </xsl:if>
               <xsl:if test="@instock = 'Y'">
                  <tr>             
                     <td><xsl:value-of select="customerid"/></td>
                     <td><xsl:value-of select="status"/></td>
                     <td><xsl:value-of select="name"/></td>
                     <td><xsl:value-of select="price"/></td>
                     <td><xsl:value-of select="qty"/></td>
                  </tr>
               </xsl:if>
            </xsl:for-each>
            </table>
         </body>

      </html>
   </xsl:template>

</xsl:stylesheet>

My desired output is a table of all Item orders in a table, sorted by Itemid, and if instock = "N" then it should highlight that row. The table should have Customerid, Status, Item Name, Item Price, and Item Qty for each row.

Upvotes: 0

Views: 35

Answers (1)

Martin Honnen
Martin Honnen

Reputation: 167691

Use relative expressions inside templates or xsl:for-each which change the context node:

 <xsl:for-each select="//item">
           <xsl:sort select="@itemid"/>
           ...
           <td><xsl:value-of select="../customerid"/></td>

I would also shorten

           <xsl:if test="@instock = 'N'">
              <tr style="background-color:yellow">             
                 <td><xsl:value-of select="customerid"/></td>
                 <td><xsl:value-of select="status"/></td>
                 <td><xsl:value-of select="name"/></td>
                 <td><xsl:value-of select="price"/></td>
                 <td><xsl:value-of select="qty"/></td>
              </tr>
           </xsl:if>
           <xsl:if test="@instock = 'Y'">
              <tr>             
                 <td><xsl:value-of select="customerid"/></td>
                 <td><xsl:value-of select="status"/></td>
                 <td><xsl:value-of select="name"/></td>
                 <td><xsl:value-of select="price"/></td>
                 <td><xsl:value-of select="qty"/></td>
              </tr>
           </xsl:if>

to

              <tr>    
                 <xsl:if test="@instock = 'N'">
                    <xsl:attribute name="style">background-color: yellow;</xsl:attribute>
                 </xsl:if>        
                 <td><xsl:value-of select="../customerid"/></td>
                 <td><xsl:value-of select="../status"/></td>
                 <td><xsl:value-of select="name"/></td>
                 <td><xsl:value-of select="price"/></td>
                 <td><xsl:value-of select="qty"/></td>
              </tr>

Upvotes: 1

Related Questions