Here's the general idea... do a split() on the search values. Then do a for-each on each of those values to see if your product atttributes contain that value.
Thanks for your reply. However I'm not sure this will work in this case.
Hopefully this clarifies it, here's pretty much what I'm trying to do
<xsl:variable name="searchterm">,3,1,</xsl:variable>
<xsl:variable name="productattributes">,1,7,3,2,</xsl:variable>
<xsl:if test="contains($searchterm, $productattributes)">
(this returns false, but I need a function to return True
as the product has both '1' and '3' as attributes and therefore should return in the search)
</xsl:if>
The way in theory I could solve this are:
Sort the search term = (,1,3,)
Loop through all the product attributes and remove any attributes not in the search term = (,1,3,)
Sort the filtered product attributes = (,1,3,)
Then see if they match - contains(',1,3,' , ',1,3,') = True
A 'contains' won't work as that will match the string that you're getting from your search term. In the example above, the productattributes does not contain the string ",1,3,". So, I think what you would need (borrowing from Dougs example above) is something like this:
Now, if we had access to 2.0 then we could have done an index-of, but since we don't then this rather (potentially) expensive nested loop is the best approach (as I see it).
Chris, I tried your code but got the following error:
System.Xml.Xsl.XslTransformException: To use a result tree fragment in a path expression, first convert it to a node-set using the msxsl:node-set() function.
Using this code:
<xsl:variable name="searchterms">1369,1064</xsl:variable>
<xsl:variable name="productattributes">1064,1372,1369</xsl:variable>
<xsl:if test="contains(umbraco.library:Split($productattributes/value,','), umbraco.library:Split($searchterms/value,','))">
Match
</xsl:if>
Real shame because that would have been perfect, please let me know if I've coded it incorrectly.
Nik, I'm close to get it all working using an expensive loop similar to your code, which may have to do for now!
Would be interested to hear any other solutions too, prehaps using C# / LINQ?
Problem is you're doing the split on $productattributes/value, the /value part should be appended to the split function, since the split function returns a node set of value nodes beneath a values node. And you don't need to do a split, on both strings, just one of them, and then use contains with prepended and appended commas to match exact id's like this:
Thanks for your reply, however unless I'm mistaken your code will match products with EITHER attribute 1369 OR 1064.
The problem is that I want to return only products which have match ALL search terms.
Hence I need to loop through and keep hold of the values somehow, unless there was some call to the CONTAINS function which would do this, something similar to Chris's code, which unfortunately I couldn't get to work.
Looks like a expensive loop is the only way to go in XSLT?
I ran into a similar problem when making a related pages xslt file based on tags. To solve it I created a temp nodeset and saved all matches there. Then another nodeset where I grouped the matches and weighted them. Performance wise not the best, but seems to work fine with the website I made it for at least. The weighting (which just counts how many times a specific node has been listed in the temp nodeset) could be used to find the correct matches.
Matching multiple comma separated values
Hi,
In XSLT how would I achieve the following?
I have comma seperated search values of (1,2,8)
I need to see which products have all these attributes, so for example
Product 1 attributes - (1,3,4)
Product 2 attributes - (1,2,3,4,5,8,10)
Product 3 attributes - (1,2,5,8)
So in this example Product 2 & 3 would match as they both have attributes of 1, 2 & 8.
I'm not looking for advice on the structure and nodes as such as I've have this in place, just the problem above!
Would appreciate any advice, many thanks
Rich
Hi, Rich,
Here's the general idea... do a split() on the search values. Then do a for-each on each of those values to see if your product atttributes contain that value.
Something like this (not tested):
cheers,
doug.
Hey Doug,
Thanks for your reply. However I'm not sure this will work in this case.
Hopefully this clarifies it, here's pretty much what I'm trying to do
<xsl:variable name="searchterm">,3,1,</xsl:variable> <xsl:variable name="productattributes">,1,7,3,2,</xsl:variable> <xsl:if test="contains($searchterm, $productattributes)"> (this returns false, but I need a function to return True as the product has both '1' and '3' as attributes and therefore should return in the search) </xsl:if>
The way in theory I could solve this are:
Rich
Hi Rich,
A 'contains' won't work as that will match the string that you're getting from your search term. In the example above, the productattributes does not contain the string ",1,3,". So, I think what you would need (borrowing from Dougs example above) is something like this:
Now, if we had access to 2.0 then we could have done an index-of, but since we don't then this rather (potentially) expensive nested loop is the best approach (as I see it).
Hope this works.
-- Nik
Hi Rich,
I'd still try the 'split' approach as I had a very similar problem recently and this worked for me. try
You may have to run a split on the first list too (I can't quite remember if I had to do that).
This should also avoid any complex looping
Cheers,
Chris
Hi Chris / Nik,
Thanks for your replies.
Chris, I tried your code but got the following error:
Using this code:
<xsl:variable name="searchterms">1369,1064</xsl:variable> <xsl:variable name="productattributes">1064,1372,1369</xsl:variable> <xsl:if test="contains(umbraco.library:Split($productattributes/value,','), umbraco.library:Split($searchterms/value,','))"> Match </xsl:if>
Real shame because that would have been perfect, please let me know if I've coded it incorrectly.
Nik, I'm close to get it all working using an expensive loop similar to your code, which may have to do for now!
Would be interested to hear any other solutions too, prehaps using C# / LINQ?
Cheers
Rich
Hi Rich
Problem is you're doing the split on $productattributes/value, the /value part should be appended to the split function, since the split function returns a node set of value nodes beneath a values node. And you don't need to do a split, on both strings, just one of them, and then use contains with prepended and appended commas to match exact id's like this:
Regards
Jesper Hauge
Hi Jesper,
Thanks for your reply, however unless I'm mistaken your code will match products with EITHER attribute 1369 OR 1064.
The problem is that I want to return only products which have match ALL search terms.
Hence I need to loop through and keep hold of the values somehow, unless there was some call to the CONTAINS function which would do this, something similar to Chris's code, which unfortunately I couldn't get to work.
Looks like a expensive loop is the only way to go in XSLT?
Cheers
Rich
I ran into a similar problem when making a related pages xslt file based on tags. To solve it I created a temp nodeset and saved all matches there. Then another nodeset where I grouped the matches and weighted them. Performance wise not the best, but seems to work fine with the website I made it for at least. The weighting (which just counts how many times a specific node has been listed in the temp nodeset) could be used to find the correct matches.
is working on a reply...