How to sort in XSLT given user defined order

0

Given the following order of status: Best Worst 0, 1, 2, 3, 4, 5, 6, G, U, Q, ., V, R, I, X, D

How do i sort below and get the worst:

<Details>
  <status>U</status>
</Details>
<Details>
  <status>0</status>
</Details>
<Details>
  <status>X</status>
</Details>
<Details>
  <status>D</status>
</Details>
<Details>
  <status>1</status>
</Details>
<Details>
  <status>2</status>
</Details>

I tried encoding the status to numbers then sorting and getting maximum value, but having issues:

<xsl:variable name="MaxWorstStatus">
    <xsl:for-each select="//ic:Details/ic:status">
        <xsl:variable name="Status">
            <xsl:call-template name="encodeStatus">
                <xsl:with-param name="Node" select="."/>                                                 
            </xsl:call-template>                                     
        </xsl:variable>
        <xsl:sort select="$Status" data-type="text" order="descending"/>                                         
        <xsl:if test="position() = 1"><xsl:value-of select="$Status"/</xsl:if>
    </xsl:for-each>
</xsl:variable>

<xsl:template name="encodeStatus">
    <xsl:param name="Node"/>
    <xsl:choose>
        <xsl:when test="$Node='U'">7</xsl:when>
        <xsl:when test="$Node='G'">8</xsl:when>
        <xsl:when test="$Node='Q'">9</xsl:when>
        <xsl:when test="$Node='.'">10</xsl:when>
        <xsl:when test="$Node='V'">11</xsl:when>
        <xsl:when test="$Node='R'">12</xsl:when>
        <xsl:when test="$Node='I'">13</xsl:when>
        <xsl:when test="$Node='X'">14</xsl:when>
        <xsl:when test="$Node='D'">15</xsl:when>
        <xsl:otherwise>
            <xsl:value-of select="$Node"/>
        </xsl:otherwise>
    </xsl:choose>
</xsl:template>

I am expecting to return 15 but getting the following error: Code: 0x80004005 Keyword xsl:sort may not be used here.

xml
xslt
asked on Stack Overflow Jul 19, 2019 by Paul Nario

1 Answer

0

If your possible status values are all going to be 1 character, you can define a variable like so:

<xsl:variable name="order">0123456GUQ.VRIXD</xsl:variable>

And then your sort becomes this...

<xsl:sort select="string-length(substring-before($order, .))" data-type="number" order="descending"/>

Try this xsl:for-each instead

  <xsl:for-each select="//ic:Details/ic:status">
    <xsl:sort select="string-length(substring-before($order, .))" data-type="number" order="descending"/>                                         
    <xsl:if test="position() = 1">
      <xsl:value-of select="string-length(substring-before($order, .))"/>
    </xsl:if>
  </xsl:for-each>
answered on Stack Overflow Jul 19, 2019 by Tim C • edited Jul 19, 2019 by Tim C

User contributions licensed under CC BY-SA 3.0