Solved

Viewstate Errors when loading dynamic user control

Posted on 2010-08-24
16
3,199 Views
Last Modified: 2012-05-10
Hi all,

I've a really annoying problem with viewstate that I can't seem to figure out. I've an aspx page which dynamically loads web user controls into a panel. It loads about 10 user controls, 1 at a time. However, only 3 are causing issues.

FYI, I'm loading the user controls in the onint event as below:

protected override void OnInit(EventArgs e)
        {
            //If we're loading for the first time load default page.
            if (Session["wuc_location"] == null)
           {
               Session["wuc_location"] = "default_wuc.ascx";
               Session["wuc_ID"] = "WUC_default_wuc";
           }
           else
           {
               //Choose which WUC to load based on button clicked!
               switch ((string)Request.Form["__EVENTTARGET"])
               {
                   case "LinkButton_MM_Inbox":
                       Session["wuc_location"] = "administration_wuc.ascx";
                       Session["wuc_ID"] = "WUC_administration_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   case "LinkButton_MM_System_Logs":
                       Session["wuc_location"] = "logs_main_wuc.ascx";
                       Session["wuc_ID"] = "WUC_logs_main_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   case "LinkButton_MM_Preferences":
                       Session["wuc_location"] = "user_preferences_wuc.ascx";
                       Session["wuc_ID"] = "WUC_user_preferences_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   case "LinkButton_P20T":
                       Session["wuc_location"] = "previous_20_transactions_wuc.ascx";
                       Session["wuc_ID"] = "WUC_previous_20_transactions_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   case "WUC_administration_wuc$LinkButton_ADMIN_SMS_Settings":
                       Session["wuc_location"] = "sms_settings_wuc.ascx";
                       Session["wuc_ID"] = "WUC_sms_settings_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   case "WUC_administration_wuc$LinkButton_ADMIN_Department_Setup":
                       Session["wuc_location"] = "department_setup_wuc.ascx";
                       Session["wuc_ID"] = "WUC_department_setup_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   case "WUC_administration_wuc$LinkButton_ADMIN_Terminal_Setup":
                       Session["wuc_location"] = "terminal_setup_wuc.ascx";
                       Session["wuc_ID"] = "WUC_terminal_setup_wuc";
                       Session["Page_First_Load"] = true;
                       break;
                   
                   default:
                       //
                       break;
               }
           }

            //Load the selected user control
            Main_PH.Controls.Clear();
            WUC_default_wuc = new Control();
            WUC_default_wuc = this.LoadControl((string)Session["wuc_location"]);
            WUC_default_wuc.ID = (string)Session["wuc_ID"];
            Main_PH.Controls.Add(WUC_default_wuc);
            base.OnInit(e);
        }

Open in new window


I've deleted a lot of "cases" in the switch above to reduce the size of the code.

So below is one of the problems I'm having:

The aspx page has a menu on the left with links such as ADMINISTRATION, SYSTEM LOGS, USER PREFERENCES - If I click on Administration, the wuc_administration.ascx is loaded into Main_PH. I could have another 10 links from within administration.ascx - 1 in particular is the SMS settings page. Clicking on SMS settings loads:

case "WUC_administration_wuc$LinkButton_ADMIN_SMS_Settings":
                       Session["wuc_location"] = "sms_settings_wuc.ascx";
                       Session["wuc_ID"] = "WUC_sms_settings_wuc";
                       Session["Page_First_Load"] = true;
                       break;

Open in new window


Now if I click on the USER PREFERENCES link on the left menu which loads:

case "LinkButton_MM_Preferences":
                       Session["wuc_location"] = "user_preferences_wuc.ascx";
                       Session["wuc_ID"] = "WUC_user_preferences_wuc";
                       Session["Page_First_Load"] = true;
                       break;

Open in new window


I get a view state error:

Microsoft JScript runtime error: Sys.WebForms.PageRequestManagerServerErrorException: Failed to load viewstate.  The control tree into which viewstate is being loaded must match the control tree that was used to save viewstate during the previous request.  For example, when adding controls dynamically, the controls added during a post-back must match the type and position of the controls added during the initial request.

Its driving me insane. I understand Viewstate and the way it works... but I don't see how I could be getting viewstate errors when a user control is removed and a new one is added? This error only occurs when traversing from certain user controls. I could go to the email settings control and then to the user preferences control with no problem.....

I'd appreciate any help on the matter at all!!!
0
Comment
Question by:Sunny_Kumar
  • 9
  • 6
16 Comments
 
LVL 14

Expert Comment

by:Dhanasekaran Sengodan
Comment Utility
Add following line in  web.config


<system.web>
<pages validateRequest="false" enableEventValidation="false" viewStateEncryptionMode="Never"> </pages>
</system.web>

Open in new window

0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi Dhansmani,

The code above made no difference. I added it as below (as they was already a pages tag)

[code]
<pages controlRenderingCompatibilityVersion="3.5" clientIDMode="AutoID" validateRequest="false"
           enableEventValidation="false" viewStateEncryptionMode="Never">
      <controls>
                        <add tagPrefix="telerik" namespace="Telerik.Web.UI" assembly="Telerik.Web.UI"/>
                  </controls>
            </pages>
[/code]

Thanks for trying to help! Any other suggestions?
0
 
LVL 16

Expert Comment

by:Vikram Singh Saini
Comment Utility
Hi,

If some are working and some not delete all temporary files in TemporaryASP.NET folder. And let us know the result back.

Regards,
VSS
0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi,

I tried deleting the files and it didn't work..... Anything else?
0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Ok guys I have an interesting update here.

I've attached 3 images:
1. - A screen of sms settings (sms.jpg)
2. - A screen of user preferences (user_pref.jpg)
3. - A screen of user preferences after I swap the 2nd dropdown for a label. (user_pref1.jpg)

Screen 3 is the most important. After the user_preferences_wuc.ascx control kept throwing the viewstate error when you click to it from sms_settings_wuc.ascx, I got rid of the 2nd dropdown from user preferences and replaced it with a label:

[code]
<asp:Label ID="Label1" runat="server" Text="Label"></asp:Label>
[/code]

When I did this, the result was screen 3. There was no viewstate error but the label got populated with the viewstate from the previous sms_settings_wuc.ascx control..... How is this possible?????? Can somebody shed some light on what is happening??
sms.jpg
User-pref.jpg
User-pref1.jpg
0
 
LVL 16

Expert Comment

by:Vikram Singh Saini
Comment Utility
Hi,

After reading your whole code and having look on snapshot of your website I reached at some conclusion. Please rectify me if I am wrong at some point. What I am sharing with you is based on my theoretical knowledge of the concept.

Here we go: (Trying to understand your problem and sharing solution)
(1) All your menu items on left side are linkbutton. And you are opening particular user control dynamically on basis of click event of particular button.

(2) Since controls are being created in Page_OnInit event, so it would not create problem of saving ViewState of each dynamic controls created.

(3) On loading Administration control (User Control) the inner controls (such as links & with link click other controls) of Admin are also loading. And here is the doubt or solution.

You said you are having 10 links in Admin usercontrol. So whether these controls are also being created dynamically or are they also user control. If they are also user controls, then it means creation of user control within user control. And I think this is disturbing the tree control hierarchy of controls which is being created when your page is posted back to the server. And since your new controls created in usercontrol are now when posted back are causing problem.

Solution for this could be to clear all viewstate of these controls by method protected void ClearChildViewState ()

And for your last comment problem statement:

When I did this, the result was screen 3. There was no viewstate  error but the label got populated with the viewstate from the previous  sms_settings_wuc.ascx control..... How is this possible?????? Can  somebody shed some light on what is happening??

So for that again my answer would be messing of viewstate of controls. Since your mobile number label is probably name as Label1 and of User preference is also name Label1 (this is my assumption). So since the value of Label1 for sms one is already saved in viewstate and when your control's (user preference) label1 value goes with updated value but there is already saved value of the label1 so it replace it with that one.

All knowledge I shared with you is based on the topic I studied at link:
http://msdn.microsoft.com/en-us/library/ms972976.aspx

Regards,
V.S.Saini
0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi Vs,

To answer your questions:

Points 1,2 and 3 are correct.

But the 10 links you mention are not created dynamically: They are created at design-time like so

[code]
 <div class="admin_a">
                    <asp:LinkButton ID="LinkButton_ADMIN_CompanySetup" OnClick="ajax_cp_admin_Click" runat="server">
                    Company Setup
                    </asp:LinkButton>
                </div>
                <div class="admin_a">
                    <asp:LinkButton ID="LinkButton_ADMIN_Preferences" OnClick="ajax_cp_admin_Click" runat="server">
                    User Preferences
                    </asp:LinkButton>
                </div>
                <div class="admin_a">
                    <asp:LinkButton ID="LinkButton_ADMIN_Languages" OnClick="ajax_cp_admin_Click" runat="server">
                    Language Setup
                    </asp:LinkButton>
                </div>
            <div class="admin_a">
                    <asp:LinkButton ID="LinkButton_ADMIN_Currencies" OnClick="ajax_cp_admin_Click" runat="server">
                    Currency Setup
                    </asp:LinkButton>
                </div>
[/code]

There is only 1 panel on the page where user controls are loaded and that is Main_PH. As you can see above (and below for reference), this panel is cleared of controls during Ajax postbacks and then the correct control is re-added:

[code]
Main_PH.Controls.Clear();
            WUC_default_wuc = new Control();
            WUC_default_wuc = this.LoadControl((string)Session["wuc_location"]);
            WUC_default_wuc.ID = (string)Session["wuc_ID"];
            Main_PH.Controls.Add(WUC_default_wuc);
[/code]

Regarding the re-writing of the label in user_prefences_wuc.ascx when traversing from sms_settings_wuc.ascx.... the id of the Label is user pref is label1... the id of the label in sms_settings is Label_SMS_Number1....

I don't understand why this is happening. The Viewstate from the SMS user control is being loaded into the Viewstate of User Preferences control
0
 
LVL 16

Expert Comment

by:Vikram Singh Saini
Comment Utility
Hi,

So we are facing problem of ViewState management (overall). And all this unexpected behaviour of program is due to viewstate mixing up. So we would need to get control to ViewState information of page directly and clean it.

But before that I would like to know from your side. Is there any problem if we clear all values of viewstate explicitly. Also have look on link: http://stackoverflow.com/questions/354195/inconsistent-behavior-with-ajax-and-viewstate-in-net Might you get some idea.

Regards,
VSS
0
Highfive + Dolby Voice = No More Audio Complaints!

Poor audio quality is one of the top reasons people don’t use video conferencing. Get the crispest, clearest audio powered by Dolby Voice in every meeting. Highfive and Dolby Voice deliver the best video conferencing and audio experience for every meeting and every room.

 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi,

I don't think there is any problem clearing viewstate as long as its at the correct point. I.e. When a new control is added as below:

switch ((string)Request.Form["__EVENTTARGET"])
               {
                   case "LinkButton_MM_Inbox":
                       Session["wuc_location"] = "administration_wuc.ascx";
                       Session["wuc_ID"] = "WUC_administration_wuc";
                       Session["Page_First_Load"] = true;
                       break; ..... etc

I'll read that article this morning thank you.

Thank you very much for taking your time to help me. It is very much appreciated!
0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi Vs,

I've looked over that article but I don't see how it applies to my case? That person is looking to utlise the viewstate where as I just want to reset it / wipe it... There doesn't seem to be a method to wipe the viewstate.
0
 
LVL 16

Expert Comment

by:Vikram Singh Saini
Comment Utility
Hi,

There is and it is Control.ClearChildViewState Method

Please check link for more details:
http://msdn.microsoft.com/en-us/library/system.web.ui.control.clearchildviewstate%28v=VS.71%29.aspx

Regards,
VSS


0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi,

I did actually try that method but it did not make any difference.

I am having some success though. User preferences and Sms settings user controls have the same number of controls inside them. I added a placeholder around the whole of the sms settings user control and it seemed to solve my problems.

For some reason ASP.net is getting confused between user controls even though the user control locations and IDs are completely different. The only thing they have in common is the number of child controls they hold. Encapsulating the sms settings child controls within a placeholder has stopped any errors....

Although this is fixed for now I'd still love to know exactly why ASP.net viewstate was getting confused??
0
 
LVL 16

Accepted Solution

by:
Vikram Singh Saini earned 500 total points
Comment Utility
Hi,

Would you please check if the following link provides you some solution for your problem:
http://forums.asp.net/t/1274992.aspx

There they says for:

1. EnableEventValidation="false"
2. Set ViewState="false"
3. just redirect the page again (I too don't understand what they mean to say)

Regards,
V.S.Saini
0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi VS,

My solution uses Ajax so redirecting is not an option. View state is needed in my solution too so that is not an option.

And EventValidation is a good thing, I don't want to disable it.
http://odetocode.com/blogs/scott/archive/2006/03/20/asp-net-event-validation-and-invalid-callback-or-postback-argument.aspx

As I said its working now even though viewstate has a bug it seems. Points for being very helpful! I do appreciate your time and effort!
0
 
LVL 1

Author Comment

by:Sunny_Kumar
Comment Utility
Hi Vs, (and others!)

Just to let you know I have solved this. The problem was this. In my page OnInit method where I load the user control, I was also adding it. This is very wrong apparently as viewstate looks for the old user control after the OnInit method. Viewstate does not know that the control has changed.

To fix this problem I change the onInit method to just load the control and not add it as below:

            WUC_default_wuc = new Control();
            WUC_default_wuc = Page.LoadControl((string)Session["wuc_location"]);
            WUC_default_wuc.ID = (string)Session["wuc_ID"];

The Page_onLoad method is the correct place to load the user control.

protected void Page_Load(object sender, EventArgs e)
        {
            Main_PH.Controls.Add(WUC_default_wuc);
}


And now everything works :) :) I really hope this helps somebody out there. Its caused problems for me for a very long time!
0
 
LVL 16

Expert Comment

by:Vikram Singh Saini
Comment Utility
Hi,

So this is called Research & Development. And really on working this question I too learned many new concepts and codes related with AJAX and ViewState.

And yes I searched lot for it on internet but the solution there were also based on developer's experience. It will be really fruitful to anyone reading the whole discussion and finally reaching to the solution.

Happy Coding :-)

Regards,
VSS
0

Featured Post

Top 6 Sources for Identifying Threat Actor TTPs

Understanding your enemy is essential. These six sources will help you identify the most popular threat actor tactics, techniques, and procedures (TTPs).

Join & Write a Comment

This article is for Object-Oriented Programming (OOP) beginners. An Interface contains declarations of events, indexers, methods and/or properties. Any class which implements the Interface should provide the concrete implementation for each Inter…
Exception Handling is in the core of any application that is able to dignify its name. In this article, I'll guide you through the process of writing a DRY (Don't Repeat Yourself) Exception Handling mechanism, using Aspect Oriented Programming.
It is a freely distributed piece of software for such tasks as photo retouching, image composition and image authoring. It works on many operating systems, in many languages.
Get a first impression of how PRTG looks and learn how it works.   This video is a short introduction to PRTG, as an initial overview or as a quick start for new PRTG users.

743 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

22 Experts available now in Live!

Get 1:1 Help Now