While working on migrating a 2009 Event System to 2013 SP1, I was looking at a requirement implemented to ensure that publishing actions to Live are always mirrored on Staging – thus making sure that Staging also has the latest versions of content, and indeed has old content removed without relying on the Editors remembering to check the Staging checkbox on the Publish popup. The existing code was rather complex, but when I tried playing around with the 2013 Event System in .NET, I found it was rather simple to implement…
The existing code used the OnPage|Component|StructureGroupPublishPost events, and drilled into the XML of the PublishResponse to find the target, and if it was Live, call the .Publish method of the item with some properties mapped from the original publish action (like ActivateBlueprinting), but with the Staging target instead of Live. My main issue with the logic was that it didn’t seem to take into account the fact that the Editor might have already selected both Live and Staging when publishing, so a duplicate Staging publish might occur, taking up unnecessary publishing bandwidth. On top of this it is also possible to publish Taxonomies and Templates and this was not taken into account
After a bit of thought I came to the solution – I have to say that the way .NET event handlers have been set up made it almost too easy. Using RepositoryLocalObject as the subject and PublishOrUnPublishEventArgs as the Event arguments its easy, we just need to check if the staging target is in the args.Targets, and if not add it.
This means we have a neat, one method handler, applying to all publishable items, for publish and unpublish, and we will never get duplicate publish transactions to staging, as if the Editor has selected Staging as a target, we can detect this and simply do nothing.