Redirecting without the exceptions...

I was doing some load testing the other year and noticed one of the counters was going off the charts - ASP.Net exceptions.  I couldn't understand why my application, which was behaving fine in every other way, was throwing exceptions.

It turned out that I have been doing a Response.Redirect from the OnInit of a Page that was inheriting from a custom Page class which had a try/catch. The exception was a ThreadAbortException.  I quickly added a catch clause to grab the ThreadAbortException and ignore it, but what could I have done to avoid throwing an exception at all?

One of the most common calls in the whole of ASP.Net is Response.Redirect - which sends an HTTP 302 response back to the browser and does one of the most common things that all multi-threaded system do - throws a ThreadAbortException to exit the current Thread.

It turns out that there is another way to do this, assuming you can handle the conditional logic to ensure the current Response doesn't get mashed up before you send it to the browser.  It involves the little-known CompleteRequest() method, which essentially tells ASP.Net to skip any more events in the Pipeline, Handler or Module and just send the Response straight back to the client.

Here's my example of redirection method that doesn't throw an Exception.

As you can see - the only "customized" piece of logic is where we set the StatusCode of the Response to 302 (the 300 series of response codes are all different kinds of redirects, but 302 seems to do the trick for whatever you need).  The rest of the method just sets properties of the Response object (like RedirectLocation).

The net effect?  The same as Response.Redirect - except no exception. :)

Rock on - joel.

Published Thursday, November 20, 2008 9:38 AM by joelvarty
Filed under: ,

Comments

# re: Redirecting without the exceptions...

Thursday, November 20, 2008 10:22 AM by richardneverett

Response.Redirect has an overload that has a second boolean argument called "endResponse".

If this is set to false, then no exception will be thrown. Note however that any code that follows the Response.Redirect will still execute.

# re: Redirecting without the exceptions...

Thursday, November 20, 2008 10:35 AM by joelvarty

Agreed, Richard.  

The only real reason to have a custom method is to ensure that "CompleteRequest()" gets called internally and not Request.End().

# re: Redirecting without the exceptions...

Thursday, November 20, 2008 12:51 PM by Brendan

Nice. Adding this to my project now.

Can you just post the code in plain-text next time instead of putting it into a PNG?

# Interesting Finds: 2008.11.21~2008.11.25

Monday, November 24, 2008 8:18 PM by gOODiDEA.NET

.NET Redirecting without the exceptions So, what’s new in the CLR 4.0 GC? Source Control for Visual

# Interesting Finds: 2008.11.21~2008.11.25

Monday, November 24, 2008 8:19 PM by gOODiDEA

.NETRedirectingwithouttheexceptionsSo,what’snewintheCLR4.0GC?SourceControlforVisu...

# re: Redirecting without the exceptions...

Tuesday, November 25, 2008 11:56 AM by bob

"which essentially tells ASP.Net to skip any more events in the Pipeline, Handler or Module and just send the Request straight back to the client."

Joel in this context shouldn't it be "Response" not "Request"?

# re: Redirecting without the exceptions...

Tuesday, November 25, 2008 12:30 PM by joelvarty

yes - you are correct bob.  My bad.  Editing that part of the post.

# re: Redirecting without the exceptions...

Wednesday, December 24, 2008 4:33 AM by RaynaldM

Great solution for redirect on IE Mobile, without MobilePage def

# re: Redirecting without the exceptions...

Monday, September 14, 2009 8:29 PM by Charles

I tried this but the code after keeps executing.  Perhaps because I am calling it from Page_PreInit?

Leave a Comment

(required) 
(required) 
(optional)
(required)