A
Andy Dingley
I have a publishing application. The database layer queries various
sources and produces an XML document, then XSLT processes this into HTML
or RSS.
In this particular case, there are several queries for the latest
articles from various "chapters" (news, reviews etc), these are then
placed as sub-trees in the XML. I then need to generate a single list of
articles by selecting the articles from each sub-tree.
It's possible for an article to be "multi-homed", so it might appear in
two chapters. My output must filter these, so that an article appears no
more than once.
As the XML document contains duplicated articles (duplicates of single
database articles), it's not possible to use generate-id() here. Instead
I must use the @articleid attribute. I'm also finding it impractical to
use a preceding-sibling:: axis, because these articles come from
disjoint sub-trees and so aren't siblings. For platform portability
reasons, I'm reluctant to use node-set()
What's the best way to diambiguate these ?
At present it works, but the code is a mess. Rather than filtering them
and then passing the filtered set neatly to the output routine, I'm
having to pass the set with duplicates to a named template, then filter
it inside that, using position(). I'd prefer to decouple the filter and
the loop processing, for other reasons of good code structure.
Thanks for any comments
<xsl:variable name="items" select="$item-headline-article
| $items-news [position () <= 4]
| $items-reviews [position () <= 3]
| $items-competition" />
[...]
<xsl:for-each select="$items" >
<xsl:variable name="entry" select="." />
<xsl:variable name="articleid" select="$entry/@articleid" />
<xsl:variable name="idx" select="position ()" />
<xsl:if test="not ($entries [($articleid = ./@articleid)
and (position() < $idx) ] ) " >
[...]
</xsl:if>
</xsl:for-each>
sources and produces an XML document, then XSLT processes this into HTML
or RSS.
In this particular case, there are several queries for the latest
articles from various "chapters" (news, reviews etc), these are then
placed as sub-trees in the XML. I then need to generate a single list of
articles by selecting the articles from each sub-tree.
It's possible for an article to be "multi-homed", so it might appear in
two chapters. My output must filter these, so that an article appears no
more than once.
As the XML document contains duplicated articles (duplicates of single
database articles), it's not possible to use generate-id() here. Instead
I must use the @articleid attribute. I'm also finding it impractical to
use a preceding-sibling:: axis, because these articles come from
disjoint sub-trees and so aren't siblings. For platform portability
reasons, I'm reluctant to use node-set()
What's the best way to diambiguate these ?
At present it works, but the code is a mess. Rather than filtering them
and then passing the filtered set neatly to the output routine, I'm
having to pass the set with duplicates to a named template, then filter
it inside that, using position(). I'd prefer to decouple the filter and
the loop processing, for other reasons of good code structure.
Thanks for any comments
<xsl:variable name="items" select="$item-headline-article
| $items-news [position () <= 4]
| $items-reviews [position () <= 3]
| $items-competition" />
[...]
<xsl:for-each select="$items" >
<xsl:variable name="entry" select="." />
<xsl:variable name="articleid" select="$entry/@articleid" />
<xsl:variable name="idx" select="position ()" />
<xsl:if test="not ($entries [($articleid = ./@articleid)
and (position() < $idx) ] ) " >
[...]
</xsl:if>
</xsl:for-each>