Re: passing a parameter to select attribute of <xsl:sort>

Subject: Re: passing a parameter to select attribute of <xsl:sort>
From: Jeni Tennison <jeni@xxxxxxxxxxxxxxxx>
Date: Wed, 21 Jun 2000 20:44:25 +0100

The simple answer, I'm afraid, is "you can't do that".  Here's why:

>	I am trying to pass a parameter into a sort element through another
>template as follows:
><xsl:apply-templates select="list">
>	<xsl:with-param name="title">Sort By Id:</xsl:with-param>
>	<xsl:with-param name="order">ascending</xsl:with-param>
>	<xsl:with-param name="orderingElement">./person/id</xsl:with-param>

When you set the $orderingElement parameter there, you are setting the parameter to the string "./person/id".  When you use it:

><xsl:template match="list">
>	<xsl:apply-templates select="./listItem">
>		<xsl:sort order="{$order}" select="$orderingElement"/>
>	</xsl:apply-templates>

it's equivalent to saying:

  <xsl:sort order="ascending" select="'./person/id'" />

which isn't the same as:

  <xsl:sort order="ascending" select="./person/id" />

There are a couple of ways that you could get around it.  The first is to use an extension function that converts a string into an XPath expression.  For example, with SAXON you could use:

  <xsl:sort order="{$order}" select="saxon:evaluate($orderingElement)" />

provided that you've identified the 'saxon' namespace as "";, and (of course) that you're using SAXON.  If you're not, the XSLT processor you're using may have an equivalent extension function.

The second is more complicated and needs to be handcrafted depending on the range of values that $orderingElement can take, but sticks within the limits of the XSLT Recommendation.  If you only ever sort on the id, firstName and lastName of the person, for example, then you could set the parameter to whichever of those was applicable, e.g.:

  <xsl:with-param name="orderingElement" select="'id'" />

and then construct an XPath around that name, e.g.:

  <xsl:apply-templates select="./listItem">
    <xsl:sort order="{$order}"
              select="./person/*[name() = $orderingElement]"/>

Or you could have a big xsl:choose that determined what to sort on based on the value of the $orderingElement parameter, but that is a tad unwieldy.

I hope that goes some way towards helping, anyway.



Dr Jeni Tennison
Epistemics Ltd * Strelley Hall * Nottingham * NG8 6PE
tel: 0115 906 1301 * fax: 0115 906 1304 * email: jeni.tennison@xxxxxxxxxxxxxxxx

 XSL-List info and archive:

Current Thread