Contracts with .NET 4.0 Code - How Will They Affect Unit Testing?

For example, this article introduces them.

What is the advantage?

Static analysis seems cool, but at the same time, it prevents the possibility of passing null as a parameter to the unit test. (if you followed the example in the article)

While on the topic of unit testing - considering how now, of course, it makes no sense to conclude contracts for code if you already practice automatic testing?

Update

Playing with code contracts, I'm a little disappointed. For example, based on the code in the accepted answer:

public double CalculateTotal(Order order) { Contract.Requires(order != null); Contract.Ensures(Contract.Result<double>() >= 0); return 2.0; } 

For unit testing, you still have to write tests to ensure that null cannot be passed, and the result is greater than or equal to zero if the contracts are business logic. In other words, if I were to remove the first contract, the tests would not break if I did not have a test for this function. This is not based on using static analysis built into the best (final, etc.) Visual Studio editions.

In fact, they all boil down to alternative spelling of traditional if statements. My experience of actually using TDD with code contracts shows why and how I talked about it.

+37
unit-testing code-contracts
Sep 05 '09 at 15:02
source share
4 answers

I don’t think that unit testing and contracts really interfere with each other, and if anything, contracts should help unit testing, since it eliminates the need to add tedious repeating tests for invalid arguments. Contracts determine the minimum level that you can expect from a function, while unit tests try to verify the actual behavior for a specific set of inputs. Consider this contrived example:

 public class Order { public IEnumerable Items { get; } } public class OrderCalculator { public double CalculateTotal(Order order) { Contract.Requires(order != null); Contract.Ensures(Contract.Result<double>() >= 0); return 2.0; } } 

Obviously, the code satisfies the contract, but you still need unit testing to actually test it, as you would expect.

+37
Sep 05 '09 at 15:35
source share

What is the advantage?

Say you want to make sure that the method never returns null . Now with unit tests, you need to write a bunch of test cases in which you call a method with different inputs and make sure that the output is not zero. The problem is that you cannot test all possible inputs.

With code contracts, you simply declare that the method never returns null . A static analyzer will complain if it is impossible to prove. If he does not complain, you know that your statement is correct for all possible inputs.

Less work, a guarantee of excellence. What do not like?

+27
Sep 06 '09 at 0:17
source share

Contracts let you tell you what the actual purpose of the code is, and not allow it, no matter what the code does, with any random arguments that it executes as a definition from the point of view of the compiler, or by the code that follows the reader. This can significantly improve static analysis and code optimization.

For example, if I declare an integer parameter (using contractual notation) in the range of 1 to 10, and I have a local array in my declared function of the same size that is indexed by the parameter, the compiler may say that it is not possible to index the error, thereby creating the best code.

You can specify that null is valid in the contract.

The purpose of unit testing is to dynamically verify that the code reaches any stated goal. Just because you wrote a contract for a function does not mean that the code does this, or that static analysis can verify the code. Single testing will not disappear.

+4
Sep 05 '09 at 15:23
source share

Well, that will not interfere with general testing at all. But, as I saw, you mentioned something about TDD.

If I think about it from this point of view, I assume that he can / can change the procedure from the standard

  • create method (signature only)
  • create Unit test -> run test
  • run the test: let it not work
  • implement the method, hack it to the end to make it work.
  • run the test: see passing
  • reorganize your (possibly dirty) method
  • (repeat the test to see that you did not break anything)

This will be a very complicated unit testing procedure. In this context, I think you could insert code contracts between the 1st and 2nd points, for example

  • create method (signature only)
  • insert code contracts for input method parameters
  • create Unit test -> run test
  • ...

The advantage that I see at the moment is that you can write simpler unit tests in the sense that you will not need to check all the possible paths, since some of them are already taken into account by your specific contracts. It just gives you additional verification, but it does not replace unit testing, as there will always be more logic in the code, more path that should be tested with unit tests, as usual.

Edit

Another possibility that I had not previously considered would be to add code contracts in terms of refactoring. Basically, as an additional way to secure things. But somehow it would be superfluous, and since people do not like to do superfluous things ...

+3
Sep 05 '09 at 15:43
source share



All Articles