Variations.Current.UserAccessibleLabels can spawn lots of SPWebs

Be careful when using the OOTB SharePoint Publishing property Variations.Current.UserAccessibleLabels as it spawns SPWebs for every call.

To demo this I’ve created a web part and added 2 different code blocks to it with monitored scopes. The first one creates 3 objects with a direct reference to the UserAccessibleLabels property. The second one uses a local field which is only assigned once.

namespace TestVariations.TestAccessibleLabels
{
    [ToolboxItemAttribute(false)]
    public partial class TestAccessibleLabels : WebPart
    {
        private ReadOnlyCollection<VariationLabel> userAccessibleLables = null;

        public ReadOnlyCollection<VariationLabel> UserAccessibleLables
        {
            get
            {
                if (userAccessibleLables == null)
                    userAccessibleLables = Variations.Current.UserAccessibleLabels;

                return userAccessibleLables;
            }
        }

        public TestAccessibleLabels()
        {
        }

        protected override void OnInit(EventArgs e)
        {
            base.OnInit(e);
            InitializeControl();
        }

        protected void Page_Load(object sender, EventArgs e)
        {
            try
            {
                var resultBuilder = new StringBuilder();

                using (new SPMonitoredScope("Variations.Current.UserAccessibleLabels"))
                {
                    var variationLabels = Variations.Current.UserAccessibleLabels;
                    var variationLabels2 = Variations.Current.UserAccessibleLabels;
                    var variationLabels3 = Variations.Current.UserAccessibleLabels;

                    foreach (var label in variationLabels)
                    {
                        resultBuilder.Append(label.Title);
                    }

                    foreach (var label2 in variationLabels2)
                    {
                        resultBuilder.Append(label2.Title);
                    }

                    foreach (var label3 in variationLabels3)
                    {
                        resultBuilder.Append(label3.Title);
                    }
                }

                using (new SPMonitoredScope("this.UserAccessibleLabels"))
                {
                    var variationLabels4 = this.UserAccessibleLables;
                    var variationLabels5 = this.UserAccessibleLables;
                    var variationLabels6 = this.UserAccessibleLables;

                    foreach (var label4 in variationLabels4)
                    {
                        resultBuilder.Append(label4.Title);
                    }

                    foreach (var label5 in variationLabels5)
                    {
                        resultBuilder.Append(label5.Title);
                    }

                    foreach (var label6 in variationLabels6)
                    {
                        resultBuilder.Append(label6.Title);
                    }
                }

                resultLabel.Text = resultBuilder.ToString();
            }
            catch (Exception ex)
            {
                resultLabel.Text = ex.Message;
            }
        }
    }
}

If we take a look at the developer dashboard, we can see SPWebs getting generated for each variation:

spweb spawns

Using ILSpy we can see that SharePoint opens web objects to check the current user’s access.

ilspy variations

When taking a look at the loading time, we see that the impact on the total loading time is quite high when using lots of direct references.

spweb monitored scopes

For the conclusion we can say that using the OOTB SharePoint property is the way to go when you only have to use it once. However when you’re using this property all over the place in your code it’s best to keep the “result” of the UserAccessibleLabels in a private field.

Advertisements

Leave a Reply

Please log in using one of these methods to post your comment:

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