Check In other users items

UPDATE: this is now available for download on the Sitecore Marketplace

We had a request from a client for non-administrator users to be able to unlock other users locked Items.

A perfectly valid request, as the client had sensibly limited the number of Administrator users, and wanted this task handled by “Elevated Non-Admin Users”.

To start you have to understand how locking works. When a user locks an item for editing, it becomes that users property, so to speak, nobody else can edit this version of an item until it has been checked back in. works perfectly for the job in is intended for.

However, say an editor leaves the organisation, is on holiday, or otherwise unable to access Sitecore, but you need to edit one of their locked items?

Well, generally you would get a site Administrator to unlock it. But if you are trying to limit the number of users with “Admin” privileges, which is best practice, you need a way around this feature.

So how do you get around this I hear you cry?

We override it, well the item:checkin command anyway

With the help of a handy CLR class browser (ILSpy etc) you can see what is going on with the Checkin function.

We extracted the code from the class as set in the commands.config file (Sitecore.Shell.Framework.Commands.CheckIn,Sitecore.Kernel)

We created our own version of this, amended the code to allow memebers of a configured role to action the command, then patched in the change using a config include file, job done

if you want to implement this customisation, head over to the Sitecore marketplace, or see the code below.

If you require any customisation of your own, please get in touch

Code:

using Sitecore;
using Sitecore.Common;
using Sitecore.Data;
using Sitecore.Data.Fields;
using Sitecore.Data.Items;
using Sitecore.Data.Locking;
using Sitecore.Diagnostics;
using Sitecore.Globalization;
using Sitecore.SecurityModel;
using Sitecore.Shell.Framework.Commands;
using Sitecore.Web.UI.Sheer;
using System;
using System.Collections.Specialized;

namespace Arktouros.Modules
{

    [System.Serializable]
    public class CheckIn : Command
    {
        public override void Execute(CommandContext context)
        {
            Assert.ArgumentNotNull(context, "context");
            if (context.Items.Length != 1)
            {
                return;
            }
            Item item = context.Items[0];
            System.Collections.Specialized.NameValueCollection nameValueCollection = new System.Collections.Specialized.NameValueCollection();
            nameValueCollection["id"] = item.ID.ToString();
            nameValueCollection["language"] = item.Language.ToString();
            nameValueCollection["version"] = item.Version.ToString();
            Context.ClientPage.Start(this, "Run", nameValueCollection);
        }

        public override CommandState QueryState(CommandContext context)
        {
            Assert.ArgumentNotNull(context, "context");
            if (context.Items.Length != 1)
            {
                return CommandState.Hidden;
            }
            Item item = context.Items[0];
            //addition to allow for other users
            if (Context.User.IsAdministrator || Context.User.IsInRole(Sitecore.Configuration.Settings.GetSetting("Arktouros.Modules.UnlockItemsRole")))
            {
                if (!item.Locking.IsLocked())
                {
                    return CommandState.Hidden;
                }
                return CommandState.Enabled;
            }
            else
            {
                if (item.Appearance.ReadOnly)
                {
                    return CommandState.Disabled;
                }
                if (!item.Access.CanWrite())
                {
                    return CommandState.Disabled;
                }
                if (!item.Locking.HasLock())
                {
                    return CommandState.Disabled;
                }
                if (!item.Access.CanWriteLanguage())
                {
                    return CommandState.Disabled;
                }
                return base.QueryState(context);
            }
        }

        protected void Run(ClientPipelineArgs args)
        {
            Assert.ArgumentNotNull(args, "args");
            if (!SheerResponse.CheckModified())
            {
                return;
            }
            string itemPath = args.Parameters["id"];
            string name = args.Parameters["language"];
            string value = args.Parameters["version"];
            Item itemNotNull = Client.GetItemNotNull(itemPath, Language.Parse(name), Sitecore.Data.Version.Parse(value));
            //addition to allow for other users
            if (!itemNotNull.Locking.HasLock() && !Context.IsAdministrator && !Context.User.IsInRole(Sitecore.Configuration.Settings.GetSetting("Arktouros.Modules.UnlockItemsRole")))
            {
                return;
            }
            Log.Audit(this, "Check in: {0}", new string[]
                                                {
                                                                AuditFormatter.FormatItem(itemNotNull)
                                                });
            itemNotNull.Editing.BeginEdit();
            itemNotNull.Locking.Unlock();
            LockField lockField = itemNotNull.Fields[FieldIDs.Lock];
            if (lockField != null)
            {
                using (new SecurityDisabler())
                {
                    lockField.ReleaseLock();
                }
            }
            itemNotNull.Editing.EndEdit();
            Context.ClientPage.SendMessage(this, "item:checkedin");
        }
    }
}

Configuration:

<configuration xmlns:patch="http://www.sitecore.net/xmlconfig/">
  <sitecore>
    <commands>
      <!-- patch into web.config -->
      <command  patch:instead="*[@name='item:checkin']" name="item:checkin" type=" Arktouros.Modules.CheckIn, Arktouros.Modules" />
    </commands>
    <settings>
      <!-- role to grant users ability to unlock other users locked items -->
      <setting name="Arktouros.Modules.UnlockItemsRole" value="sitecore\UnlockItems" />
    </settings>
  </sitecore>
</configuration>

 

Job done, time for a beer

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