How I Learned to Stop Worrying and Love Sitecores Live Mode

IMAGE HERE - dr_strange_love.jpg

By: Steve Bridges, Lead Consultant – Recently, I was working on a client site and something odd came up during testing. One of the navigation components were showing sporadic duplicates. It was unrelated to what we changed, we were pointing to a development database with "less than perfect" data, etc – all the reason in the world to justify dismissing it, but my conscience and curiosity wouldn't let it go.

So I started digging – sure I’d immediately find some bad data and fix it so we could all sleep better at night.

The problem was – the content was fine. So much for simple.

Then I remembered we were in Live Mode – pointing to the Master database – and therefore the indexes driving this navigation was a master database index which was not filtering on latest version correctly.

What you say? How can this be?

It’s a simple config file change to make this work, right?

Just enable the stock livemode.config and get on with your life right?

…Until you use an index…ahh – no that still works!

…Until you use an index and start creating multiple versions of content…Uh Oh!

IMAGE HERE - so_then_i_told_them.jpg. Float to the right of above text

Sitecore's default crawler (Sitecore.Search.Crawlers.DatabaseCrawler) indexes ALL versions and doesn't handle publishing restrictions. It plain isn't suitable for front-end use in live mode out of the box.

So how do we fix it?

Option One: Create a custom crawler to only add what we want to the index
Option Two: Add an inbound filter to restrict to the latest version

I chose option two due to the specifics of the project and time line. It is the least amount of code and can easily and safely be implemented in CM / Live environment only, without affecting the CD environments.

However, as detailed in multiple articles from the Sitecore Community, notably Martin English (implementing suggestions by Pavel Veller), if we aren't careful with our inbound filter, it can be a "disaster waiting to happen". See the comments on Alex Shyba's post here for more details, but the short version is that, using an inbound filter for the latest version could potentially block the removal of old versions from the index, creating the very scenario we are trying to avoid!

So my quick and dirty version – as suggested by Varun Nehra in response to Martin's solution is to not just exclude old versions from being added, but to explicitly delete them from the index. Simple. Thanks, Varun!

    public class RestrictToLatestVersion : InboundIndexFilterProcessor
    {
        public override void Process(InboundIndexFilterArgs args)
        {
            var indexableItem = args.IndexableToIndex as Sitecore.ContentSearch.SitecoreIndexableItem;

            if (indexableItem != null && !indexableItem.Item.Versions.IsLatestVersion())
            {
                args.IsExcluded = true;
                using (var context = ContentSearchManager.GetIndex(indexableItem).CreateDeleteContext())
                {
                    context.Delete(indexableItem.UniqueId);
                }
            }
        }
    }