views:

958

answers:

9

Do you use Design by Contract professionally? Is it something you have to do from the beginning of a project, or can you change gears and start to incorporate it into your software development lifecycle? What have you found to be the pros/cons of the design approach?

I came across the Design by Contract approach in a grad school course. In the academic setting, it seemed to be a pretty useful technique. But I don't currently use Design by Contract professionally, and I don't know any other developers that are using it. It would be good to hear about its actual usage from the SO crowd.

+8  A: 

I can't recommend it highly enough. It's particularly nice if you have a suite that takes inline documentation contract specifications, like so:

// @returns null iff x = 0
public foo(int x) {
  ...
}

and turns them into generated unit tests, like so:

public test_foo_returns_null_iff_x_equals_0() {
  assertNull foo(0);
}

That way, you can actually see the tests you're running, but they're auto-generated. Generated tests shouldn't be checked into source control, by the way.

James A. Rosen
Any recommendations of open-source software that does this for C#/.NET?
Mark A. Nicolosi
+3  A: 

It's absolutely foolish to not design by contract when doing anything in an SOA realm, and it's always helpful if you're working on any sort of modular work, where bits & pieces might be swapped out later on, especially if any black boxen are involved.

Greg Hurlman
+1  A: 

In lieu of more expressive type systems, I would absolutely use design by contract on military grade projects.

For weakly typed languages or languages with dynamic scope (PHP, JavaScript), functional contracts are also very handy.

For everything else, I would toss it aside an rely upon beta testers and unit tests.

Gaius: A Null Pointer exception gets thrown for you automatically by the runtime, there is no benefit to testing that stuff in the function prologue. If you are more interested in documentation, then I would use annotations that can be used with static analyzers and the like (to make sure the code isn't breaking your annotations for example).

A stronger type system coupled with Design by Contract seems to be the way to go. Take a look at Spec# for an example:

The Spec# programming language. 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.

Frank Krueger
Can you justify your first sentence (particularly “in lieu of”)? It certainly seems controversial enough, what with the US military taking the exact opposite route (which brought us Ada …). Your last sentence also seems to contradict it. I also want to point out that expressive type systems can be harnessed perfectly to *provide* contracts, through static type checking.
Konrad Rudolph
A: 

I don't actually use Design by Contract, on a daily basis. I do, however know that it has been incorporated into the D language, as part of the language.

Brad Gilbert
Unfortunately it has not been incorporated into the D standard libraries which makes the whole DbC almost useless in practice.
Lothar
+3  A: 

If you look into STL, boost, MFC, ATL and many open source projects, you can see there are so many ASSERTION statements and that makes project going further more safely.

Design-By-Contract! It really works in real product.

popopome
The STL probably isn’t the best example of design by contract. Basically, the STL policy is that “if the user did something wrong, all guarantees are voided, feel free to wreck the system.” The assertions you mentioned are only triggered in debug mode. Error handling in optimized C++ code is notoriously fickle.
Konrad Rudolph
+1 I don't think debug assertions are contracts.
ragu.pattabi
+2  A: 

Frank Krueger writes:

Gaius: A Null Pointer exception gets thrown for you automatically by the runtime, there is no benefit to testing that stuff in the function prologue.

I have two responses to this:

  1. Null was just an example. For square(x), I'd want to test that the square root of the result is (approximately) the value of the parameter. For setters, I'd want to test that the value actually changed. For atomic operations, I'd want to check that all component operations succeeded or all failed (really one test for success and n tests for failure). For factory methods in weakly-typed languages, I want to check that the right kind of object is returned. The list goes on and on. Basically, anything that can be tested in one line of code is a very good candidate for a code contract in a prologue comment.

  2. I disagree that you shouldn't test things because they generate runtime exceptions. If anything, you should test things that might generate runtime exceptions. I like runtime exceptions because they make the system fail fast, which helps debugging. But the null in the example was a result value for some possible input. There's an argument to be made for never returning null, but if you're going to, you should test it.

James A. Rosen
+3  A: 

You really get to appreciate design by contract when you have an interface between to applications that have to talk to each other.

Without contracts this situation quickly becomes a game of blame tennis. The teams keep knocking accusations back and forth and huge amounts of time get wasted.

With a contract, the blame is clear.

Did the caller satisfy the preconditions? If not the client team need to fix it.

Given a valid request, did the receiver satisfy the post conditions? If not the server team need to fix that.

Did both parties adhere to the contract, but the result is unsatisfactory? The contract is insufficient and the issue needs to be escalated.

For this you don't need to have the contracts implemented in the form of assertions, you just need to make sure they are documented and agreed on by all parties.

Ged Byrne
+1  A: 

Both Unit testing and Design by Contract are valuable test approaches in my experince.

I have tried using Design by Contract in a System Automatic Testing framework and my experience is that is gives a flexibility and possibilities not easily obtained by unit testing. For example its possible to run longer sequence and verify that the respons times are within limits every time an action is executed.

Looking at the presentations at InfoQ it appears that Design by contract is a valuable addition to the conventional Unit tests in the integration phase of components. For example it possible to create a mock interface first and then use the component after- or when a new version of a component is released.

I have not found a toolkit covering all my design requirement to design by contract testing in the .Net/Microsoft platform.

A: 

Yes, it does! Actually a few years ago, I designed a little framework for Argument Validation. I was doing a SOA project, in which the different back-end system, did all kind of validation and checking. But to increase response times (in cases where the input was invalid, and to reduce to load those back-end systems), we started to validate the input parameters of the provided services. Not only for Not Null, but also for String patterns. Or values from within sets. And also the cases where parameters had dependencies between them.

Now I realize we implemented at that time a small design by contract framework :)

Here is the link for those who are interested in the small Java Argument Validation framework. Which is implemented as plain Java solution.

Verhagen