I have a Doc Type called Blog - In short everything under a content node can create a blog. Along with this is the date for the blog. I'm trying to count the number of blogs for each month using XSLT and have the below but is giving me the incorrect count?
<xsl:key name="MonthNo" match="Blog" use="substring(concat(currentDate, @createDate), 1,7)"/>
<xsl:template match="Blog" mode="month">
<xsl:variable name="DateBlog" select="concat(currentDate, @createDate)"/>
<xsl:variable name="YearBlog" select="substring-before($DateBlog, '-')"/>
<xsl:variable name="MonthBlog" select="substring($DateBlog,6,2)"/>
<xsl:variable name="BlogsInMonth" select="key('MonthNo', substring($DateBlog,1,7))"/>
<li>
<xsl:element name="a">
<xsl:attribute name="href">
<xsl:value-of select="umbraco.library:NiceUrl(1234)"/>?d=<xsl:value-of select="concat($MonthBlog, '-', $YearBlog)"/>
</xsl:attribute>
<xsl:value-of select="concat($monthNames[position()=$MonthBlog], ' (', count($BlogsInMonth),')')"/>
</xsl:element>
</li>
Can anyone see where ive gone wrong or the mistake made? Struggling with this so any help is appreciated.
The way you use key
function to get the number of blogs in particular month
is corect. I created an example script, correcting a little your version
(http://xsltransform.net/pNvs5vT), take a look at it.
The source XML contains 6 Blog
nodes, one created in September, two in October
and three in November and the number is properly presented in the output.
But I have some doubts about your original script and maybe the reason that your script failed is in some other place.
Let's start with the formula you used to create the key:
use="substring(concat(currentDate, @createDate), 1,7)"
As I see, you:
currentDate
and attribute createDate
(I assume they are 2 dates formatted as yyyy-mm-dd).So the final result is yyyy-mm part of currentDate
(only).
Are you sure that this is correct? Why do you "add" createDate
?
Nothing from it is the part of the final substring.
Note that in my script I took only a single date - createDate
attribute.
If my choice is wrong, then change createDate
to currentDate
in both the script
and the source XML.
Another, maybe more important, problem with your script is that you used $monthNames[position()=$MonthBlog]
which (at least under xsltransform) generates error message:
Cannot compare xs:integer to xs:string
.
The reason is that $MonthBlog
is a string, but the required type to compare
with position()
is integer.
In my script I used $monthNames[number($MonthBlog)]
, as you can see,
applying the proper conversion and without (in this case default) position()
.
And the last important issue: You didn't specify the version of XSLT, so I used version 2.0.
So to sum up: Compare my working script with yours, maybe you will find some errors in your script.
I prepared another script, in version 1.0, see http://xsltransform.net/pNvs5vT/1.
Key differences:
Version 1.0 does not accept such constructs as sequence of strings
(like ('January','February',...)
), so I used a sequence of child nodes
instead.
The content of this variable is of Result Tree Fragment type, so to
allow to use it in XPath expressions, I had to use exsl:node-set
function.
This in turn required to put extra stuff in transform
tag and causes that
this script does not work under 2.0 version any more.
In template matching root
I used Muenchian grouping to output
li
and a
tags only for the first blog from each month, and deleted
printing of id
and createDate
from the current Blog
element.