Friday April 29th

Thursday April 28th

Wednesday April 27th

Why throw; is not allways the best way to rethrow exceptions

This blog post explains why the standard throw; approach of rethrowing exceptions is not the best in case you care of the full stack trace information

8 comments

Yeap, this is the right way,
The other previous article saying the 'rethrowing exceptions the right way' kicked to the front page needs burying in my opinion (if there was such an option..) Simply for the reason that it mislead people to believe that, that was the right way when in fact the one described here is

Seriously, does this really matter? As long as you can somehow determine the source of the error you can log it and later set a breakpoint to debug it later. How the message and the stack trace is formatted hardly matters. The important thing is to allow the exception to be raised to where it is handled instead of eating it and ignoring the problem. In ASP.NET that means handling the Application_Error event in Global.asax which is a good place to log the details and redirect to a proper error page that does not insecurely tell the user about the internals of your application. At the end of the day exceptions should be rare and if they are thrown it will be done during development where you clear them up before the software is published.

Next can we discuss what is better, using StringBuilder versus adding strings with the plus operator?

Sorry, I guess I was a little to hasty on the keyboard there! Thats true, stepping back a little and looking at the overall picture what counts is that you have some information about the error. In fact, if you are the only guy working on the development of the application this is perfectly ok. But I think it is quite important for example, in a scenario where you are creating a reusable library or component, It is good practice to make use of InnerExceptions to rethrow errors in a way this post describes. When you wrap up the exceptions like this you are more likely to throw a more meaningful error to the developers who are trying to use your library in their application. More meaningful errors = better debugging experience for those developers.

True enough. In my experience the exceptions typically happen when there is a problem with a system outside of the application, such as the remote database. Either the connection string is not valid or a stored procedure was not deployed. In that case if you simply thow the exception (throw;) it will be easy to realize the cause of the problem. Now if you have a null reference, that is another matter that is harder to track down sometimes. For WCF communications, which throw fault exceptions, you could translated the exceptions on the client and turn them into something that makes sense like a NullReferenceException when an object is not found. I recall something along these lines related to SQL or SubSonic where the exceptions related to foreign key constraints were translated into C# terms with exceptions. An example would be making a constraint violation into a invalid state exception. But in the end there is not single way to do it. Context matters.

These kinds of blog posts seem to turn up every so often, with the writer eager to point out a flaw where there is in fact none, at all.

The *only* reason that one should throw a new exception is in the event that it be necessary to change the type of exception that was thrown to something more meaningful for the intended operation. In *this* event, it should be considered a good (though not necessarily "best") practice to pass the original exception to the inner exception parameter of the new exceptions constructor. If intentions do not include changing the type of exception, there is no reason to do anything other than throw the original exception with throw.

Anastasiosyal and offwhite, make no mistake about it, exceptions can and will occur in production applications. Unless your application targets a room full of developers with a debugger at their finger tips, you should have no expectation of having a debugger to assist you with debugging, for example, a problem that seems to occur only a clients machine. The more information that your clients have to report back to you, the easier your life will be with determining the proper way to correct the issue.

Senfo,
in case you would like to log exception (e.g. create event log with Log4Net , Ent Lib block) you would catch - publish - rethrow to preserve information about it.

You can do that offcourse on one centralized place, but still you need to try catch publish :D

Even in case you don't want to wrap the exception to some custom type, I would still use inner exception because if you don't you loose a piece of stack related to defect.

That's the whole point of the blog post - loosing of stack information

Nothing I said would have prevented you from logging the exception and re-throwing it.

try
{
throw new ArgumentNullException();
}
catch (ArgumentNullException ex)
{
if (ExceptionPolicy.HandleException(ex, "DefaultPolicy"))
throw;
}


If you want to change the exception thrown, that's fine and dandy.

try
{
throw new ArgumentNullException();
}
catch (ArgumentNullException ex)
{
if (ExceptionPolicy.HandleException(ex, "DefaultPolicy"))
throw new CustomException("Something bad happened", ex);
}

When changing the exception thrown, one should ask them self , "Why do I want to change the exception being thrown?" In most situations, there is absolutely no need to change the exception, so my first example from the above post should be used. However, there certainly are situations in which it makes more sense to change the exception type to make it more clear exactly what occurred to cause the exception to be thrown in the first place.

I was recently working with a library that threw an InvalidOperationException for any kind of operation that wasn't successful. For example, if the service I was utilizing timed out while connecting to a remote server, an InvalidOperationException was thrown. If the remote server returned invalid XML, an InvalidOperationException was thrown. If a message I sent was missing a required XML attribute...you get the idea. As part of an implementation of a provider that I was building, I did my best trap any InvalidOperationException's and throw a more meaningful exception. In this situation, it made no sense to utilize the innerException parameter because the original exception contained no worthwhile information that would have assisted anybody with troubleshooting the issue. So why bother? If, and only if, I couldn't come up with an algorithm to programmatically determine what happened to cause the original exception, I simply re-threw the *original* exception. There was certainly no reason to instantiate a new Exception object and pass the original exception.

Make sense now? :D

Commenting on Stories is limited for now and will open up to those recommended by the community. Learn how
Loading DotNetKicks...
brought to you by the Kicks Network