The context() method provides a mechanism for testing the position of a node in the context of a query. To demonstrate, let's take a set of elements and display them as a comma-separated list. In this example, you need to insert a comma after each product except the last one.
The end() method can be used to determine whether the element is the last one in the query. The query ".[not(end())]" will not produce the desired results because end() is applied to the query "." when you really want it to be applied to the query "products/product" found in the preceding <xsl:for-each>. The context() refers to the correct query, and the resulting template becomes:
<DIV>
<xsl:for-each select="products/product">
<xsl:value-of /><xsl:if test="context()[not(end())]">, </xsl:if>
</xsl:for-each>
</DIV>
Since the comma is being inserted based on the position in the query and not based on the position in the source document, the list can be sorted without messing up the results. The following template shows how to add commas to a sorted product list.
<DIV>
<xsl:for-each select="products/product" order-by="-.">
<xsl:value-of /><xsl:if test="context()[not(end())]">, </xsl:if>
</xsl:for-each>
</DIV>
The order-by attribute is given the value "-." to indicate a descending sort by product name.