Hello Again,
I am trying to sort several levels of data using a XSL document. I got it to work but it is using a bunch of recursion. I am trying to avoid this because I figured using multiple sorts withing a single node shold have worked. Is there a way to change the XSL below to be less recursive? I am sorting on USER/USERID, then ROLE/@name and finally ACTIONINFO/@actionfrom
Working Stylesheet:
<xsl:template match="/">
<xsl:apply-templates select="USERACTIONINFO"/>
</xsl:template>
<xsl:template match="USERACTIONINFO">
<xsl:copy>
<xsl:for-each select="USER">
<xsl:sort select="USERID"/>
<xsl:copy>
<xsl:copy-of select="USERID" />
<xsl:for-each select="ROLE">
<xsl:sort select="@name"/>
<xsl:copy>
<xsl:copy-of select="@name" />
<xsl:apply-templates select="ACTIONINFO">
<xsl:sort select="@actionfrom"/>
</xsl:apply-templates>
</xsl:copy>
</xsl:for-each>
</xsl:copy>
</xsl:for-each>
</xsl:copy>
</xsl:template>
<xsl:template match="*|@*|text()">
<xsl:copy>
<xsl:apply-templates select="*|@*|text()">
</xsl:apply-templates>
</xsl:copy>
</xsl:template
</xsl:stylesheet>
Some XML to test with:
<USERACTIONINFO >
<USER>
<USERID>SSSUSER</USERID>
<ROLE name="ZZ_UPD">
<ACTIONINFO actionfrom="ZC" />
<ACTIONINFO actionfrom="AC" />
</ROLE>
<ROLE name="QQ_UPD">
<ACTIONINFO actionfrom="AZCC11" />
<ACTIONINFO actionfrom="ACC11" />
</ROLE>
</USER>
<USER>
<USERID>AAAUSER</USERID>
<ROLE name="PP_UPD">
<ACTIONINFO actionfrom="ZZADBENF" />
</ROLE>
<ROLE name="PP_BOEE">
<ACTIONINFO actionfrom="BOM02" />
</ROLE>
<ROLE name="PP_SS">
<ACTIONINFO actionfrom="AZDBENF" />
<ACTIONINFO actionfrom="ADDBEN" />
</ROLE>
</USER>
</USERACTIONINFO>
Actual CORRECT output:
<USERACTIONINFO>
<USER>
<USERID>AAAUSER</USERID>
<ROLE name="PP_BOEE">
<ACTIONINFO actionfrom="BOM02" />
</ROLE>
<ROLE name="PP_SS">
<ACTIONINFO actionfrom="ADDBEN" />
<ACTIONINFO actionfrom="AZDBENF" />
</ROLE>
<ROLE name="PP_UPD">
<ACTIONINFO actionfrom="ZZADBENF" />
</ROLE>
</USER>
<USER>
<USERID>SSSUSER</USERID>
<ROLE name="QQ_UPD">
<ACTIONINFO actionfrom="ACC11" />
<ACTIONINFO actionfrom="AZCC11" />
</ROLE>
<ROLE name="ZZ_UPD">
<ACTIONINFO actionfrom="AC" />
<ACTIONINFO actionfrom="ZC" />
</ROLE>
</USER>
</USERACTIONINFO>
What I thought I should be able to do but didn't work:
<xsl:stylesheet version='1.0'
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes"/>
<xsl:output omit-xml-declaration="yes"/>
<xsl:template match="/">
<xsl:apply-templates select="USERACTIONINFO"/>
</xsl:template>
<xsl:template match="USERACTIONINFO">
<xsl:copy>
<xsl:apply-templates select="USER">
<xsl:sort select="USERID"/>
<xsl:sort select="ROLE/@name"/>
<xsl:sort select="ROLE/ACTIONINFO/@actionfrom"/>
</xsl:apply-templates>
</xsl:copy>
</xsl:template>
<xsl:template match="*|@*|text()">
<xsl:copy>
<xsl:apply-templates select="*|@*|text()"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>