Wednesday, March 28, 2012

UpdateProgressControl/UpdatePanel timeout

I have a main ASP.NET 2.0 web form (C# code-behind) that has an "inbox" that displays records from a database. The main web form has a AspTimer control and an UpdatePanel control that are used in concert to refresh the inbox every 2 minutes (120000ms) triggered by the timers Tick event. However, when a user creates a new record using another web form I am triggering an async refresh of the inbox (after the record is saved) by calling a javascript function (via ModalPopupExtender OnOkScript value) that detects the presence of a hidden button on the main form and firing it's click event which is handled as an asp:AsyncPostbackTrigger for the main web forms update panel. Everything works as designed, but from time to time after the remote page triggered refresh occurs the next timer refresh (Tick event) or other user initiated event (e.g. gridview row select, sort) will hang and result in an "Sys.WebForms.PageRequestManager TimeoutException: The Server request timed out."error. I am not sure if the remote page triggered refresh is confusing the AspTimer somehow or it is causing a collision of some sorts but any thoughts on the matter would be much appreciated.

Further details/update: Once I get the "Sys.WebForms.PageRequestManagerTimeoutException" error, I can consistentely get it to occur by clicking a button that triggers an async postback. It's as if the session has lost it's connection (note that this happens regardless if I am running against my local development machine (XP/IIS51) or our test server (2003/IIS6)). The very weird thing that is befuddling me is that if I use fiddler to watch the traffic to see what is going on it (the connection) will be magically restored and everything works fine again. There are no server side errors being thrown and JavaScript console in (NS/FireFox) does not show anything that would point me to a resolution.


Eureka!!! I figured out the problem. I have JavaScript methods that are called by my child forms when a user is clicking the "Close/Cancel" button that verify there are no unsaved changes before closing otherwise user is prompted to verify that they want to discard changes or not. If they confirmed that they wanted to close the web form I was simply calling window.close() but was not returning any value from the function which I think was a problem because the Close/Cancel button is located within the update panel (because the image changes depending on the scope of the form (e.g. new or view)) and thus despite closing the window I think the AJAX event lifecycle was being initiated but terminated abnormally because of the form closing. I added a "return false;" in my finally clause for all the functions that are used in the closing of a child web form and lo and behold my parent form no longer breaks (see example function below - added statement is bolded). I hope this solution also works for anyone else having a similar problem:

// Function Name: CloseVisitLog
// Function Purpose: Close the visit log form.
// Author: Michael Jensen
function CloseVisitLog(scope)
{
// put function within try-catch-finally block
try
{
// debug statement - set debug = true to view
if (debug) alert(">>Entered JavaScript:CloseVisitLog");

// declare local variables
var unsavedChanges = GetUnsavedChangesFlag();

if(scope == "new")
{
// make sure the user really wants to cancel
if (confirm("Are you sure you want to cancel creation of this visit log entry?"))
{
// close the window
window.close();
}
else
{
return false;
}
}
else if(scope == "view")
{
// if there are unsaved changes make sure the user really
// wants to close
if(unsavedChanges == "true")
{
if (confirm("There are unsaved changes, are you sure you want to close?"))
{
// close the window
window.close();
}
else
{
return false;
}
}
else
{
// close the window
window.close();
}
}
}
catch(ex)
{
var msg = "JavaScript:CloseVisitLog failed. ";
alert(msg + ex.messsage);
}
finally
{
// debug statement = set debug = true to view
if (debug) alert("<<Exiting JavaScript:CloseVisitLog");
// return false to prevent postback when window is closing
// otherwise parent form AJAX will break
return false;
}
}

No comments:

Post a Comment