Using page trace to reduce your ViewState in SharePoint

Search

Accessible SharePoint WebSites
Download ARF

Using page trace to reduce your ViewState in SharePoint

http://blog.thekid.me.uk

ViewState is useful for saving a control's state across page post backs, but is does no good at all if you are navigating via links...the ViewState is only ever used during a POST not a GET. If you have a SharePoint publishing site (or even a collaboration site) then the majority of navigation will be via links in the content and not post backs. This makes a vast amount of the ViewState redundant and so can safely be removed.

By default ASP.Net controls have their ViewState on and so is the case with SharePoint controls...this leads to an ever growing ViewState in the page, which I have seen over 20k in size.

Its always worthwhile trying to reduce the footprint of your ViewState as it makes the pages load faster on the client and reduces the processing on the server. Fortunately there is an easy way to see where the ViewState is produced and to check if your efforts have reduced it.

Page Trace

By far the easiest way to see what is creating your pages ViewState is to turn page tracing on in web.config...

image

Once this is on then you can use trace.axd to see the trace output from the page request. If you are doing this remotely from the server then you will need to add the attribute localOnly=false. You could also set pageOutput=true so that you don't need to access trace.axd and get the required information directly in the requested page.

The page trace output contains a section called 'Control Tree' and this section can be used to see the size of your ViewState and the controls which are producing it...

image

Here you see the two SharePoint menu controls are producing 384 & 280 bytes of ViewState . Generally this ViewState will not be used for anything and just takes time to build on the server, send to the client and for the client to parse.

The above trace output shows the ViewState created by the default page of the 'Press Releases' subsite in a standard MOSS publishing site. This template has only one subsite and so has very little navigation. Below is the output for the same page when only a further five subsites are added...

image

As you can see the ViewState has increased by 512 bytes and will continue to increase the more sites, pages or subsites are included in the navigation. As this is a SharePoint website there are going to be very few postbacks which will utilize this ViewState and so removing it will improve the performance.

Modifying the master page

In order to remove the ViewState we need to change the master page, in my case the BlueBand.master. You will need to find all the <SharePoint:AspMenu> controls and add a parameter of EnableViewState=False...

image

This is the left navigation ViewState before turning the ViewState off...

image

And after...

image

That's 952 bytes of ViewState saved and that's with only six items in the navigation. Many have over 30 items and could be saving over 5k of ViewState in each request. By turning off the view state for all AspMenu controls will save a fair bit of overhead in the weight of the page.

Using the BlueBand master page on the 'Press Releases' home page will generate 3,156 bytes of ViewState, by disabling the ViewState for the three navigation controls in the master page this will be reduced to 2,320 bytes. By disabling the SiteActions ViewState it will be reduced to 2,088 bytes and finally by disabling it on the Welcome ascx it will be reduced to 1,412 bytes. This is less than half the original.

Going further with some development

Other ViewState culprits in SharePoint are the Field Controls, these generate ViewState even if they are only displaying HTML and not allowing authoring...

image

The image above shows the FieldValue control, which only ever displays the content of a field...its still using ViewState and 224 bytes at that. This happens to be the Page Title in the header and so to display 20 bytes for the text of the title the client is actually having to download 244 bytes...All field controls appear to produce at least 224 bytes of ViewState.

The main problem with SharePoint field controls is that they actually rely on the ViewState during editing and so you cannot just disable it...they will stop working when you edit the page. However we can use the fact that whether ViewState is enabled or not is inherited from the controls parent. Using this fact we can selectively disable the ViewState when the page is just being displayed.

By creating a container control we can control the ViewState of the controls it contains...

public class ViewStatePanel : Control
{
    protected override void OnInit(EventArgs e)
    {
        if (SPContext.Current.FormContext.FormMode == Microsoft.SharePoint.WebControls.SPControlMode.Display)
            EnableViewState = false;

        base.OnInit(e);
    }

    protected override void Render(HtmlTextWriter writer)
    {
        RenderChildren(writer);
    }
}

This control can then be used to 'wrap' the offending SharePoint field controls and control their ViewState...

image

This will then reduce you ViewState even further. By modifying the WelcomeLinks.aspx page layout with the new container the final reduction in ViewState for an OOTB SharePoint publishing site was from an original 3,156 bytes down to 1,048 bytes...less than a third of what it was originally.

This is a fairly small reduction, but then its only a small site two pages and one subsite. You should be able to get much larger reductions using this technique in your own projects.

Try it for yourself

If you would like to try the ViewState container for yourself you can download the DLL and make the following changes.

1. Add the DLL to the GAC (or the bin folder and change trust to Full).

2. Add the following to the SafeControls in web.config

<SafeControl Assembly="TheKid.ViewState, Version=1.0.0.0, Culture=neutral, PublicKeyToken=4e73ec0fe752cafb" Namespace="TheKid.ViewState" TypeName="*" Safe="True" />

3. Add the following line to the top of your layout page

<%@ Register Tagprefix="TheKid" Namespace="TheKid.ViewState" Assembly="TheKid.ViewState, Version=1.0.0.0, Culture=neutral, PublicKeyToken=4e73ec0fe752cafb" %>

4. Wrap the controls for which you wish the ViewState to be controlled with <TheKid:ViewStatePanel runat="server">

Posted by Vincent Rothwell on Wednesday, 3 Sep 2008 16:24  - 6 Comments
Orininally printed from http://thekid.me.uk - Copyright Vincent Rothwell 2007
 

Comments

Monday, 8 Sep 2008 11:25 by Tyler Holmes
Nice post Vincent. It's good to see you're still around and posting ;-). Keep em coming man you do great work. Best, Tyler

Tuesday, 9 Sep 2008 07:32 by Vince
Tyler, Thanks for that --Vince

Thursday, 11 Sep 2008 07:30 by kulwant
nice code for me like Master page modification

Wednesday, 15 Oct 2008 05:50 by axel
Hy there, great post, again. Your name suites you really well. Without having tried it, would it also be possible to use this mechanism for Web Part Zones? Greatly appreciate your advice. axel

Wednesday, 6 May 2009 09:14 by Rik
Does anyone know how they have done this for the site of www.ferrari.com ? We have so many fieldcontrols on so many pages i was hoping to find a more "global" approach than doing this for one control at a time... All suggestions are more than welcome! Kind regards, Rik

Wednesday, 9 Jun 2010 03:34 by sam
Hi, Thanks for the extremely informative and helpful documents. Cheers,



Url

Email

Comments