Welcome to Tech-Review.Org Sign in | Join | Help

.net_2.0

My coding blog entries. Typically will either be more complex coding examples or overcoming product issues / troubleshooting resolutions.
Comments on: Sys.WebForms.PageRequestManagerParserErrorException - what it is and how to avoid it

Elion Lipton recently wrote - Sys.WebForms.PageRequestManagerParserErrorException - what it is and how to avoid it, which explains some of the reasons the PageRequestManagerParserErrorException occurs.

 

Please, take this in the spirit it is intended - it is not a rant or complaint, just my own personal observations on the reasons. I do not intend to stomp on toes of such technical expert and again have to state - I do not blog to create flame wars - only merely - to 1. document my own stupity or 2. Raise additional questions or even sometimes 3. provide even more information....I do not really care how many hits my site gets as 90% of them are spam / bot hits anyways...

 

Let's look at the article step by step:

[Elion] Calls to Response.Write():
By calling Response.Write() directly you are bypassing the normal rendering mechanism of ASP.NET controls. The bits you write are going straight out to the client without further processing (well, mostly...). This means that UpdatePanel can't encode the data in its special format.

Additional Info:  For initial rendering of a page - that uses a UpdatePanel as long IF - any Response.Writes must be done before the PreRender phase of the Page load cycle.  I'll even beg to differ that you can use Response.Writes can be used during a partial update as well.  The trick is (and reference Elion's other entry on properly instigating Templates - which the same approach should be considered when usng custom controls...)... not doing a Response.Write() to the page but in a control.  I use Response.Writes in alot of custom controls in my web applications because I do not necessarily want to create labels and the such...after all - all the UpdatePanel sees is the end html rendered...

For example: You have a link control that uses Response.Write() to render a html link with a bunch of query strings.  As long as this control is rendered properly by the main page by using the "EnsureChildControls()", and before the main page's PreRender you will most likely never have an issue with this...

An example of this is Microsoft's own Trace options... If you elect to have the trace feature embed the trace at the end of the page - yes, you will have issues because the Trace will intercept the page - reformat it and spew it out - disrupting the DOM because the ScriptManager is only looking at the page rendered prior to when the Trace feature intercepts the page completed at the server but before sent to the client..Trace intercepts it and spews out the newly rendered page...If you use the Trace option and configure it as such:

<trace writeToDiagnosticsTrace="true" enabled="true" pageOutput="false" />

Trace doesn't try to rewrite the page before it is sent out - instead it creates a seperate page to view the trace and it works nicely with Ajax.  And BTW to address his:

[Elion] Server trace is enabled:
If I were going to implement trace again, I'd do it differently. Trace is effectively written out using Response.Write(), and as such messes up the special format that we use for UpdatePanel.

That is how you work around it...

However, in context he is indeed correct.  For instance if you use a Gridview in a Update Panel and use the CSS Adapter from Microsoft to revert the changes of the table format of the gridview to the CSS styling... Yep, you'll get those errors because the CSS Adapter has to intercept the page after it is rendered and change the markup and the ScriptManager is unaware... and keep in mind - it is not just the UpdatePanel that causes those errors it is the ScriptManager... it is responsible as kinda being the overbearing mother that tells the child put your jacket on...

 

[Elion] HttpModules:
Again, the same deal as Response.Write() and response filters.

 

Sigh, I have to say that it is actually totally inaccurate.  I use nothing but custom IHttpModules and coming from someone so critical in the development of Microsoft's Ajax (Sorry Elion) this is grossly misleading. If you properly constuct how your IHttpModule renders pages and observe the page life cycle and try not to do anything fancy in the end of the rendering ...(like use the CSS Adapters)... You will never see a PageManager...error..period [Less you try to reinvoke a page while it is recompiling and the ScriptManager times out before it is compiled properly - a common thing in testing].  I just find this particular mention in the top reasons you get this error misleading and totally inaccurate much like the Trace reason.  The comment misleads developers getting there heads wrapped around using custom IHttpModules [Which as a side note is now a requirement to learn how to program to with Vista and IIS7 and upcoming release of LongHorn...which again I will state - under IIS7 as well as II6 never had a issue with properly constructed controls using Response.Writes in controls as long as the control is rendered prior to the Pre-Render of the main Page]...that they can't use HTTP Handlers with Ajax...no design guidenace is given less do not use them...

When you will see this error is when you have not done one thing if you are confident in your control design skills [meaning you did it right]..and that is...

You have not reset the cached setting of your browser  and you are trying to use cached data against what the server side now says is valid... Usually occurs when you change a lot of what the server expects in terms of the client's rendered html...

or......

You have nested your try catch statements in such a way - and no longer actually handle real errors... that state information for the page becomes corrupt.  This occurs alot when you have great number of controls whose rendering processes are out of synch...  The biggest issue that those using Ajax is that they seem to forget that server side - there is no actual partial page rendering. The server still has to recreate the entire page...it has no concept of partial page unless you use ICallBack events (which I think and could be wrong - do not work 100% with Ajax - it is usually one or the other).. If you think you can be creative and just capture the asynch postback and only handle in code what the update is expected to be...boom... page out of synch because you have neglected to handle the actual page regeneration on the server-side...That's 100% of the time give you the Page error...

 

 

[Elion] Calls to Server.Transfer():
I'm not really sure why people use Server.Transfer() at all. Perhaps it's a legacy thing from Classic ASP. I'd suggest using Response.Redirect() with query string parameters or cross-page posting.

 

I actually agree, but people do.  The biggest reason is to have the url the same on a successful action, yet, the real reason is that a Sever.Transfer copies over current viewstate and control state to new page... without actually pointing to another page... The whole "Not really sure" comment again is misleading - because there are performance implications when using other methods and Server.Transfer is actually less detrimental in terms of performance than doing a Cross Page posting... Technically speaking Ajax should be able to handle this - as all the Server.Transfer does is copy over previous page state to the new page but keeping the original context of the original page yet allowing transferred page to seamlessly use previous pages controls, viewstate etc... - kinda like a combo deal.  It should actually work in Ajax as it is nothing more or less than the same feature the ModalPopUp offers in theory... just not much thought was put into it for this design so it is a limitation...Response Redirects as a substitute for Server.Transfer is not the answer as it would usually require use of query string.... using query strings is a security risk which is why alot of programmers use server.transfers [and yes I contridict myself but using query string values for image displays - however -  is not as much of a security risk..].  Not to be overally critical... but - having been involved with designing Microsoft benchmarks - there are reasons why that particular feature is included.  But, Elion is not wrong - Ajax simply doesn't work in the Server.Transfer() and that is a limitation of Ajax and how it is implemented however, there are good reasons why Server.Transfer are used...and equally number of good reasons not to use Response.Redirect or Cross page postbacks..

Secondary, you pay a perf hit for using Response.Redirects versus Server.Transfer...

Why people do not want use Response.Redirect is the fact  Ajax provides us the resources to not to have to.  Response.Redirects are even more of an issue when it comes to Ajax because of the asynchronous nature.  Usually when a Response.Redirect is issued it is in direct result of an actual postback and there is no other alternative.  Ajax is supposed to allow us to work around that by using the partial update feature.  And here is again where Elion is correct -, Server.Transfer is used in places where it shouldn't.  However, even using Response.Redirect is an issue with Ajax so there is no win here and the recommendation to use Response.Redirects again will most likely not work as expected in alot of designed scenarios... This is the difference between monolithic coding and dynamic coding models...

Another MAJOR CAUSE for Sys.PageRequestManager errors....

Not properly using Update Panels.  Say you have two UpdatePanels on a Page one containing a gridview and the other a modalpopup.  A row click event on the gridview - the modal popup is supposed to be displayed.  But because they are in seperate UpdatePanels this event will disrupt the DOM as the UpdatePanel containing the Modal will have no idea it's state is changing.  Solution - either call the Update Panel's update() in code behind (for the modal update panel) or wrap both the update panels with a master update panel. 

Verify that all of your images are properly loading.  IIS sends script ladened 404 messages that will also conversly disrupt the DOM.  Remember the PageRequestManager error is about the state info of the DOM being compared to what the server expects in order to properly 'synch' during the partial updates...

My own personal notes.

 

Microsoft's Ajax is one of those technologies very new and not yet polished possibly more limitations than features when you look at the core featureset.  Compared to Java communities plethora of options and even IBM's sudden announcement of the adoption of Ajax technologies.. on the .Net side it still catch-up..Ajax at the core of technology is java oriented after all because that is what the browser has to be programmed to... No fault to Microsoft but the core offering only has any standing because of the toolkit.  There really is not anything of the core that is all that embellishing...and that is my opinion of course..but even the toolkit.. requires so much server in terms of server load - it is quite frankly almost worth learning how to use the ICallBack features of .Net over using Ajax ....

 

But in all fairness that is the trade-off of any object oriented language provider.... Make it easy to drag and drop or educate how to do it low level and make it easily understable to the masses.. Microsoft's Ajax wins out for ease in terms of the IDE and 'plug and play' approach; but, with the misconception of the lowered impacts to overall server performance...and as a result scalablity..[and that is a whole other discussion]...

Unlike previous entries Elion has done [whom I have the utmost respect for].. this entry was by far the biggest dissapointment in terms of the weaknesses of Ajax and specifically the UpdatePanel. Instead of just tackling the issue and providing work arounds [which no matter what language or supplement technology you may adopt you may have to do], the answer to the issue is just do not do these things...Less the Server.Transfer - there are work arounds for every 'do not do' on his list that allows you to do exactly what is told do not do... and I hate it coming from Microsoft when everything is boiled down to the lowest common denominator when knowing quite well those folks at ComponentArt and Telerick know something we do not...and what they know versus most of us developer's (myself included) is how to write controls..and trust me they use more of the do not's more so than as much as I do...

 

Microsoft Ajax is no longer in Beta, and it is quite frankly distressing the more no's than can do's because of the general overall - assume the developer skill is this level so target this level.  Again my opinion...

The biggest issue is the fact that the error message is often misleading.

1. If te developer has IE set to 'Automatically detect" this error will almost always occur especially when id's are changed.  As the user's cached settings are compared to the what should be actual settings..."

2. The ability to partially compile 'new changes' can cause this error.

3. A user that has a role expire but the page itself doesn't detect it can cause this error...

 

So, while overall Elions blog is somewhat accurate or at least accurate in the broadest sense... it is misleading in terms that it only provides merely a general synopsis of the reasons why not to do.  I probably would not have been so passionate about writing this entry other than this was a blog entry that was promoted on the forums and unlike previous explanations truly lacks actual technical substance in regards to a developer...it simply is not good enough to say do not do this because generally speaking... when in fact you can if you are educated in how to properly do it...  But, it is my opinion and certainly entitled to it... take what I say with a grain of salt ......he is afterall the author of it and I am merely just someone that tries to prove things wrong..

 

Have a dissernting point of view - please post it...

Posted: Thursday, March 01, 2007 6:52 PM by Jody
Filed under:

Comments

Microville said:

In my understanding about PageRequestManagerParserErrorException error and Trace, this will only happen If you have Trace enabled for your Page only.

So for the case like this:

<trace enabled="true" localOnly="true" pageOutput="true"/> If you change the pageOutput="false" than you won't get error (if it is just related with the Trace).

I have find one workaround if you still wants to use the PageOutput=True (Trace written to the webpage. I am using the UpdatePanel and ScriptManager.

When page Loads, We can check If the request is AsyncPostBack and we can disabled the Trace for that request.

The way we can implement is something like this:

protected void Page_Load(object sender, EventArgs e)

  {

      if(ScriptManager1.IsInAsyncPostBack)

      {

         Page.Trace.IsEnabled = false;  

      }

  }

Only dropback I know is, We will loose tracing for that particular Async Request.

# November 7, 2007 8:07 AM

Jody said:

Thanks for your response to the entry.  The deal with Asynch is that it is never actually Asynchronous. Very few items in programming are actually left to be asynchronous as asynch when programming to expect a response is different that asynch fire and forget.  

For example: A WCF client can fire off a call to something server side and want a response.  It expects that the server's asynch routines returns a response. I call this fire and wait.  Where as a logging mechanism can use asynch with a fire and forget pattern.  

What is common with Ajax is there is no such thing as fire and forget in most cases - it requires that a response is given for whatever method call is made.  Server side this always entails the entire page is loaded - there is no way around this less using web method, json, etc calls - and even then..the greater scope of things entails realizing that what do you allow to just be freely invoked via Ajax or even WCF for that matter.

Luckily with the latest builds of Ajax there are new tracing options.  But you bring up a good point - using Ajax or any other kind of asynchronous technologies - the logging and error documentation has to relate to what is being used.  

One of the things I have found is that Asynch is not the best friend in programming.  Using Asynch means you truly can break whatever was a thread safe environment and find that for example using logging of errors as an example - that things become out of synch.

I still use trace in a Ajax environment because of how I personally implement Ajax.  I realize that I want control and that Ajax for my development concerns is a UI deal but server side the whole enchilada is handled

with what I still believe a greater server load but client side it seems more fluid.  

That is one of the deals I have with like webmethod hello world examples - none contemplate what if you do want someone to say hello anyways?  

At any rate good input...  Thanks for contributing...you bring valid points to the discussion...

# November 26, 2007 11:39 PM
New Comments to this post are disabled