In applications large and small, the role of exception handling is very rarely a first class experience. Instead, it is often haphazardly put together if thought about at all. In this post, we will explore some ideas about exception handling that are often considered best practices. For the purposes of this article, assume we are building a large-scale web-based application with three tiers: UI, Logic, and Data Access.
Best Practices
Handle Each Exception Only Once…
…unless you have a very good reason not to. It is poor design to capture an exception and then rethrow it without adding value. In the mythical application we are building, if we capture an exception in the data access layer and then rethrow it and allow the business logic layer actually handle it, we have a pretty obvious code smell. Why did we capture that exception at all? Always let exceptions boil up to the layer that can handle them.
The Best Exceptions Never Happened
You should go through as much trouble as necessary to prevent exceptions from happening in common scenarios where we have a known possible error condition. For example, if you have a Contact object and you need to check the First Name of that contact, if there is any chance at all that the Contact object itself may be null, you should test for that condition to avoid an exception.
Be Consistent
This is one of the most important best practices available and is actually the reason to develop a strategy at all. Before sitting down to write an application, you should already have an exception handling strategy fully baked and ready to implement. There are few greater sins than finding ‘special cases’ in the middle of a well-thought-out exception handling policy. It goes against the grain and offends our senses. Don’t do this.
Be Specific When Possible
This one should be obvious. If you know that a SqlException may occur, catch it specifically. Try hard not to just default to catching the all-encompassing Exception type. Yes, it may require a bit more work but if you create good habits, they will serve you well for a long time.
Create Your Own Exception Classes When Necessary
Create your own exception classes to throw when it makes sense. If you constantly find yourself throwing an Exception with similar error messages, this might be an indicator of a possible exception type that should be created. There are no good hard rules here. Just do it where it makes sense to get the most bang from your buck.
Don’t Create Your Own Codes
Avoid giving codes to your exceptions. 101010 won’t mean anything compared to ‘Validation error. Field is required.’ The message makes a whole lot more sense than 101010. Please, don’t do this. It doesn’t make you smart or the system more sophisticated. The best case scenario here is that you end up being responsible for either fielding questions about what the different codes mean or publishing a list of the codes and their meanings and that means you are responsible for also keeping it up to date. Don’t you already have enough to do?
Don’t Eat Exceptions – They Are Bad For The Digestion
If you are eating or swallowing exceptions, you should have a very, very compelling reason. Why even catch them if you aren’t doing anything with them? They should, at the very least, be logged. There are certain exception scenarios that your application should be able to recover from, surely, but swallowing (ignoring) exceptions is a bad way to do that.
Logging
Again, at the very least, you should be logging every exception that occurs in your system unless you have a very good reason not to. Err on the side of caution here. Log it. If you are struggling to decide if it should be logged, go with yes, it should be. You should not log them when you have a compelling reason, not if you are indecisive.
Conclusion
If you aren’t designing an exception handling policy, you have a problem that is begging for a solution and this problem has been solved a million times. There is plenty of information out there.
In this post, we looked at some (not all) best practices that should be considered when designing an exception handling strategy. I hope you found it useful and can incorporate some of the suggestions into your own workflow and design an effective exception handling strategy.