Avoid displaying pages without a language version

The Sitecore CMS allows you to create multiple versions of the pages for each of the languages supported by your site. Still, sometimes you may want to have particular pages translated into to a certain subset of the languages, e.g. if you have French content that should be available for end users in just France and Canada. The problem is that when you try to access the page in a language which does not have a supported version, you won’t get a 404 error, but be displayed an empty page.

Now, to give you more context, assume that you want to run a competition targeted at just your UK customers. Our site has multiple languages as we have branches in many countries. We create a competition page for just the en language only. We publish the page, open it in a browser and we get:

sitecore-pages-with-no-language-version-displayed-anyway-1

However, when we try to access the page in a language that has no translation for the page, surprisingly there is no 404 page, instead we get:

sitecore-pages-with-no-language-version-displayed-anyway-2

There are several approaches how to deal with this.

Shows Not Found (404) page

Despite the fact that there is no version in Polish, pl language, we are still able to access the url. How do you avoid this? The solution, I recommend uses Sitecore processor functionality. I’ve created my own processor which is executed within httpRequestBegin just after the ItemResolver processor.

<httpRequestBegin>
    ...
    <processor type="Sitecore.Pipelines.HttpRequest.ItemResolver, Sitecore.Kernel"/>
    <processor type="AndreyVinda.SitecoreHelpers.ItemLaguageVersionValidator, AndreyVinda.SitecoreHelpers" />
    ...
</httpRequestBegin>

The code of the processor is very simple – it checks whether the current Item has any version and if there is no version, the processor assigns null to the Sitecore.Context.Item.

namespace AndreyVinda.SitecoreHelpers
{
    public class ItemLaguageVersionValidator : Sitecore.Pipelines.HttpRequest.HttpRequestProcessor
    {
        public override void Process(Sitecore.Pipelines.HttpRequest.HttpRequestArgs args)
        {
            if (Sitecore.Context.Item != null && Sitecore.Context.Item.Versions.Count == 0)
            {
                Sitecore.Context.Item = null;
            }
        }
    }
}

Now when one tries to access the page in a language that doesn’t have a translated version, a proper 404 message is displayed.

Use LanguageFallback

This is Sitecore basic knowledge but many websites don’t have a language fallback. Language Fallback is the module on the marketplace. This module is specific for multilingual items and sites. And displaying a default language for some content or ignore not translated items.

So, in case when page doesn’t have the particluar language version the redirection to the correct language language (i.e. when item has language version of the base language). A Good solution for single language websites and multilingual sites that should be 100% translated or display empty content in case a component item is not translated (Default Sitecore behavior).

The following example don’t use a pipeline like the other solution. Advantage is that it also can use without issues when working with multiple vendors in an environment. Just at the code to your masterpage (or to appropriate _Layout in case you’re using MVC).

@{
    //some code to detect if context is in the correct language, this example is for single language. And required a case sensitive correct language code in the site config
    if (Sitecore.Context.Item.Language.ToString() != Sitecore.Context.Site.Language)
    {
        var url = LanguageRedirect.GetPageWithLanguageUrlOptions(Sitecore.Context.Item,Sitecore.Context.Site.Language);
        if (!string.IsNullOrEmpty(url))
        {
            Log.Info("Language Redirect To:"+url, this);
            Response.Redirect(url);
        }
    }
}

And the source code for the Helper class

using System.Linq;
using Sitecore.Data.Items;
using Sitecore.Data.Managers;
using Sitecore.Globalization;
using Sitecore.Links;

namespace AndreyVinda.Website.Helpers
{
    public static class LanguageRedirect
    {
        public static Item GetLanguageVersion(Item item, string languageName)
        {
            var language = item.Languages.FirstOrDefault(l =&gt; l.Name == languageName);
            if (language != null)
            {
                var languageSpecificItem = global::Sitecore.Context.Database.GetItem(item.ID, language);
                if (languageSpecificItem != null &amp;&amp; languageSpecificItem.Versions.Count &gt; 0)
                {
                    return languageSpecificItem;
                }
            }
            return null;
        }
        public static string GetPageWithLanguageUrlOptions(Item item, string language)
        {
            var options = global::Sitecore.Links.LinkManager.GetDefaultUrlOptions();
            options.LanguageEmbedding = LanguageEmbedding.Always;
            options.Language = Language.Parse(language);
            options.EmbedLanguage(LanguageManager.GetLanguage(language));

            var newItem = item;
            if (item.Language.ToString() != language)
            {
                newItem = GetLanguageVersion(item, language);
            }
            if (newItem != null)
            {
                return LinkManager.GetItemUrl(newItem, options);
            }
            return string.Empty;
        }
    }
}

Enjoy!

Advertisements

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s