Quantcast
Channel: Brian Pedersen's Sitecore and .NET Blog
Viewing all articles
Browse latest Browse all 286

Sitecore Publishing – Programmatically determine if item should be published

$
0
0

Sitecore uses it’s publish settings to determine if an item should be published. But you can only control a publish from versions and date times.

Sitecore Publishing Settings

Sitecore Publishing Settings

So what if you have other values that determine if an item must be published or not? Say, a status field or a checkbox, or a combination of both? And what do you do if these fields are updated from external systems?

One way is to extend the publishItem pipeline. Every item that must be published goes through this pipeline one by one and you can therefore add a new processor that determines if an item is published or not.

AN EXAMPLE:

These are our publish options: A status field and a checkbox is updated by users and external systems to determine if this item is eligible for publishing.

Publish Options

Publish Options

The publishItem pipeline works “the other way round”, meaning that if the item can be published we leave it alone, and if not we change the publish status to “DeleteTargetItem“.

Here is my new processor (some pseudocode, apply your own checks):

using Sitecore.Data.Items;
using Sitecore.Diagnostics;
using Sitecore.Globalization;
using Sitecore.Publishing;
using Sitecore.Publishing.Pipelines.PublishItem;

namespace MyCode.Infrastructure.Pipelines.PublishItem
{
  public class DetermineActionForItem : PublishItemProcessor
  {
    public override void Process(PublishItemContext context)
    {
      // First a list of checks to ensure that
      // it is our item and we can make the decision
      // about it's publish status
      if (context == null)
        return;
      if (context.Aborted)
        return;
      Item sourceItem = context.PublishHelper.GetSourceItem(context.ItemId);
      if (sourceItem == null)
        return;
      if (!sourceItem.Paths.IsContentItem)
        return;
      // I will only check our specific item
      if (!sourceItem.TemplateName == "mytemplate")
        return;

      // OK, now we know that this is our item and
      // we can determine it's faith
      // Check every language to see if it is eligible for publishing
      foreach (Language language in sourceItem.Languages)
      {
        Item languageVersion = sourceItem.Versions.GetLatestVersion(language);
        // A little pseudocode, here is the check to see if the item can be published
        if (StatusIsOK(languageVersion["StatusField"]) && CheckBoxIsChecked(languageVersion["CheckBoxField"])
        {
          // Yes, the item can be published
          return;
        }
      }

      // No, the item cannot be published, set the publishaction == DeleteTargetItem
      Log.Info(string.Format("{0}: Unpublishing Item '{1}' from database '{2}' because it is not in the correct state.",
               GetType().Name,
               AuditFormatter.FormatItem(sourceItem),
               context.PublishContext.PublishOptions.TargetDatabase),
               this);
      context.Action = PublishAction.DeleteTargetItem;
    }
  }
}

As you can see, the function returns if the item being processed is not our item, or if the item can be published. If the item is not eligible for publishing, we change the Action to DeleteTargetItem.

The processor is added to the publish pipeline just before the Sitecore “DetermineAction” processor:

<publishItem help="Processors should derive from Sitecore.Publishing.Pipelines.PublishItem.PublishItemProcessor">
  <processor type="Sitecore.Publishing.Pipelines.PublishItem.RaiseProcessingEvent, Sitecore.Kernel"/>
  <processor type="Sitecore.Publishing.Pipelines.PublishItem.CheckVirtualItem, Sitecore.Kernel"/>
  <processor type="Sitecore.Publishing.Pipelines.PublishItem.CheckSecurity, Sitecore.Kernel"/>
  <!-- Our Processor inserted before Sitecore's "DetermineAction" proecssor -->
  <processor type="MyCode.Infrastructure.Pipelines.PublishItem.DetermineActionForItem, MyDll" />
  <!-- ... -->
  <processor type="Sitecore.Publishing.Pipelines.PublishItem.DetermineAction, Sitecore.Kernel"/>
  ...
  ...
  ...
</publishItem>

MORE TO READ:

 



Viewing all articles
Browse latest Browse all 286

Trending Articles