-
-
Save nine9ths/42283ef0480ad640cfae to your computer and use it in GitHub Desktop.
Thoughts on XSLT grouping
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!-- | |
From http://www.w3.org/TR/xslt-30/ | |
A standard grouping exercise to wrap a group of elements | |
--> | |
<xsl:template match="body"> | |
<chapter> | |
<xsl:for-each-group select="*" group-starting-with="h2"> | |
<section title="{self::h2}"> | |
<xsl:for-each select="current-group()[self::p]"> | |
<para><xsl:value-of select="."/></para> | |
</xsl:for-each> | |
</section> | |
</xsl:for-each-group> | |
</chapter> | |
</xsl:template> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!-- | |
This can be rewritten using a subtree to create a node at the group level | |
to match on. | |
--> | |
<xsl:template match="body"> | |
<chapter> | |
<xsl:for-each-group select="*" group-starting-with="h2"> | |
<xsl:variable name="group" as="element(group)"> | |
<group> | |
<xsl:sequence select="current-group()"/> | |
</group> | |
</xsl:variable> | |
<xsl:apply-templates select="$group"/> | |
</xsl:for-each-group> | |
</chapter> | |
</xsl:template> | |
<!-- | |
The problem with this method is that it breaks the context of the nodes in | |
the group. You can't do something in this template like ancestor::body/foo | |
--> | |
<xsl:template match="group"> | |
<section title="{h2}"> | |
<xsl:for-each select="p"> | |
<para><xsl:value-of select="."/></para> | |
</xsl:for-each> | |
</section> | |
</xsl:template> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!-- | |
What I'd like is to have some kind of psuedo-node e.g. group(), that | |
would be created by the for-each-group instruction that could be | |
part of a match pattern. Within the pseudo-node the current-group() elements | |
would be accessible via the child axis and the current-grouping-key() | |
function would be defined | |
--> | |
<xsl:template match="body"> | |
<chapter> | |
<xsl:for-each-group select="*" group-starting-with="h2"> | |
<xsl:apply-templates select="current-group()"/> | |
</xsl:for-each-group> | |
</chapter> | |
</xsl:template> | |
<xsl:template match="group()"> | |
<section title="{h2}"> | |
<xsl:apply-templates select="p"/> | |
</section> | |
</xsl:template> | |
<xsl:template match="p"> | |
<para><xsl:value-of select="."/></para> | |
</xsl:template> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
If you want something to match on at group level, you could use two passes that process the whole document. The first pass groups, the next pass matches on the groups. We often do multi-pass-whole-document transformations because we can save snapshots of the whole document after each pass for debugging purposes. Of course memory consumption and also transformation time may be an issue.
I don’t fathom which modifications would be necessary on the XDM in order to support this. I believe most people wouldn’t think that the benefits outweigh the additional complexity.