views:

779

answers:

4

I have been thinking about design by contract lately and I was wondering what people think is the best way to assert pre-condition and post-condition of values in .NET? i.e. validating argument values to a method.

Some people recommend Debug.Assert while others talk about using an if statement plus throwing an exception. What are the pros and cons of each?

What frameworks are available that you recommend?

+1  A: 

I prefer exceptions over asserts because if it's supposed to be that way and isn't, I want to know about it so I can fix it, and the coverage we get in debug mode is nowhere near real-life usage or coverage, so just using Debug.Assert doesn't do enough.

Using asserts means that you won't add bloat to your release code, but it means you only get to see when and why these contracts get broken if you catch them at it in a debug build.

Using exceptions means you get to see the contract breaking whenever it happens, debug or release, but it also means your release build contains more checks and code.

You could go with an inbetween approach and use Trace to trace out your pre and post conditions to some kind of application log, which you could use to debug problems. However, you'd need a way of harvesting these logs to learn what issues your users are encountering. THere is also the possibility of combing this with exceptions so you get exceptions for the more severe problems.

The way I see it though, is that if the contract is worth enforcing then its worth throwing an exception when it breaks. I think that's somewhat down to opinion and target application though. If you do throw exceptions, you probably want some form of incident reporting system that provides crash reports when raised exceptions are left unhandled.

Jeff Yates
Generally speaking the idea behind a good DBC solution involves compile time checking of post and pre conditions, giving you a tighter feedback loop over exceptions.
Jim Burger
+3  A: 

Another option is Spec#.

Spec# is an extension of the object-oriented language C#. It extends the type system to include non-null types and checked exceptions. It provides method contracts in the form of pre- and postconditions as well as object invariants.

Cameron MacFarland
Spec# is perfect for this kind of stuff if you can get it into your build environment.
Brad Wilson
A: 

Spec# is the way to do it, which is a superset of C#. Now you have "Code Contracts", which is the language-agnostic version of Spec#, so now you can have code contracts in VB.NET, for example.

Hao Wooi Lim
+2  A: 

We'll eventually use Code Contracts when .NET 4.0 ships. However, in our production code right now we have had great success with a "Guard" class along with common way to generate exceptions.

For more details, see my post about this.

Jeff Moser