Loading...
Sitecore

Override Sitecore default mechanism of getting Presentation Details


In this post I will explain how we can override default Sitecore behavior of where the presentation details are read from while rendering components. Just a single processor modification is needed to the 

mvc.getXmlBasedLayoutDefinition

pipeline.


Imagine we have a site with products. Every product has a type  and every type has a version and so on…

Car models, its types and versions can be a good example of this situation. Let’s say that every version of every type of every model is an item and can be created as a single page.

If content editor needs to add a single component to every page variant of a blue car, it would be a lot of editing. But if we know that type and version pages should have always exactly the same components as their parent car model page we can add our custom processor to

mvc.getXmlBasedLayoutDefinition

pipeline which gets XML layout for item.

All we need is:

  • Patch config
  • Overriden processor


Patch config

In pipelines section of patch config register our processor :

<pipelines>
      <mvc.getXmlBasedLayoutDefinition>
        <processor type="Assembly.Name.Processors.GetLayoutFromProductItem, Assembly.Name” patch:before="processor[@type='Sitecore.Mvc.Pipelines.Response.GetXmlBasedLayoutDefinition.GetFromLayoutField, Sitecore.Mvc']" />
      </mvc.getXmlBasedLayoutDefinition>
</pipelines>

Overriden processor

In class that inherits from GetFromLayoutField we take context or current item and just check if its template is the product (car model) template. While it’s not – we take parent – and if it finally is – we just call GetFromField with our item as parameter. It renders layout with components from product item which is car model in our case.

using Sitecore.Mvc.Pipelines.Response.GetXmlBasedLayoutDefinition;
using Sitecore.Data.Items;
using Sitecore.Mvc.Presentation;

namespace Sitecore.Extend.Layout.Processors
{
    public class GetLayoutFromProductItem: GetFromLayoutField
    {
        public override void Process(GetXmlBasedLayoutDefinitionArgs args)
        {
            if (args.Result != null)
                return;

            Item item = args.ContextItem ?? PageContext.Current.Item;
            if (item.TemplateID != ProductModelTemplateID
                && item.TemplateID != ProductTypeTemplateID)
                {
                    return;
                }
            else
            {
                while (item != null && item.TemplateID != ProductItemTemplateID)
                {
                    item = item.Parent;
                }
                if (item!= null && item.TemplateID == ProductItemTemplateID)
                    args.Result = this.GetFromField(item);
            }
        }
    }
}

And now when a product version or product type page is being rendered to end users, it gets the components from the parent product page. The data is still taken from the current item. Hence, our content editor only needs to add that one extra component to the product page itself.


Important thing is that the current item has to have a layout. It is rendered with parent layout but to run a pipeline any layout is needed in presentation details. We don’t need any renderings though.

This was just a simple example to show how extendable Sitecore can be thanks to pipelines.


One comment
Leave a Reply

Your email address will not be published. Required fields are marked *