Building a navigation system for a news or blog based on years and months (like an archive as an example) requires that we know what years and months are available for:
- The top level – as in when we open the home page
- Expanded – whenever we are viewing a month or article page and need to expand accordingly
- Dynamically – when we need to build the navigation in one shot, perhaps as an accordion or similar.
Note – we are assuming the following structure:
Its possible to code around these by doing Axes calls on the current item and getting the parents and siblings but this doesn’t scale well. Especially if you need to start dropping into sibling months to hide and show depending if they’re empty or not. And we haven’t even talked about languages.
An alternative approach is to use your Lucene index and scan it for all your news items in the current language and group them by year and month and store counts for each. Then you can cache this for even more speed.
During the course of the Sitecore installations (versions 6.2 – 7.2) I have been involved with, I have been asked to allow users to be able to select the results of their data for themselves. In later versions Sitecore have achieved this using the newer Search dialogs. I will come out and state that I haven’t really found the search dialogs too helpful as a user myself, and that I don’t see the content editors using them all that much either.
It has struck me since I first began using Sitecore that the rules engine could be an obvious potential solution to this issue. The basis being that you create a ‘query’ item, this item is then used as a datasource / basis item for your renderings (or sublayouts in older installations). I also considered the idea of combining the rules engine with Lucene / Solr in order to retrieve results based on the selection the user makes – after all, that’s what we are kinda doing as developers in any case.
I first started messing with the rules engine – shown in this post Searching with the rules engine in Sitecore. This was great and really started to show the potential. I also realised quickly that users would need to be able to test their queries from within the engine, so after a little work, I settled on a dialog that looked like this:
Just for fun – the core engine that drives this is using a simple visitor pattern and could be utilised for other data – I am currently also experimenting with my mongo L2 cache with extended linking 😀
In the next post, I will describe how to use the results of your rules queries in renderings / sublayouts or other tasks.
EDIT: For those who dont know, you can find Rules Queries for Sitecore here on Github
In this post I will be looking at using Lucinq to drive search using the default sitecore 7 indexing.
Lucinq provides the ability to use the generic forms of the standard Term, Phrase, Wildcard and other methods. This allows the assignment of an expression to denote which of the fields is the target of the query.
In the line below, you can see an example of this in action
queryBuilder.Term(t => t.Content, "value")
This tells Lucinq to read the IndexField attribute from the Content field of the SearchResultItem class and use that as the field for the Lucene query that is to be sent down.
* Note, the .HasBaseTemplate() method of Lucinq’s query extensions requires a change to the default Sitecore indexing settings. *
Here is an example in situe – this can be can in unit tests WITHOUT the need to run the sitecore initialise pipeline (unlike SC 7 search).
// the index lives in the appdata folder, so using a Server.MapPath to get the real path for Lucene.
string searchIndexPath = Server.MapPath(Settings.IndexFolder + @"/lucinqwebindex");
using (SitecoreSearch search = new SitecoreSearch(searchIndexPath))
ISitecoreQueryBuilder queryBuilder = new SitecoreQueryBuilder(SitecoreMode.Sitecore7);
queryBuilder.TemplateId(ContentIds.HomeTemplateId); // add template id to the query
// below users the sitecore index field attribute, its the same as
// queryBuilder.Term("content", "value");
queryBuilder.Term(t => t.Content, "value");// set up the term based on the in built sitecore 7 class.
ISitecoreSearchResult searchResult = search.Execute(qb);
int totalResults = searchResult.TotalHits; // gets the total number of results
List items = searchResult.GetPagedItems(1, 10);
More information can be found on Lucinq on github here
In this post I will cover using Lucinq with sitecore – in particular returning the results through the Glass Sitecore Mapper.
Returning results from lucene is something we as Sitecore developers have been used to for some time. Lucene provides hyper fast searching and its flexible storage makes it great for indexing content. However, in use, the API is somewhat verbose and not necessarily the easiest to understand without reading up on it first (I still would recommend the book Lucene In Action to get a grounding in the product).
I have a few issues with the search layers that Sitecore have implemented over the years which I won’t go into in this post.