Search code examples
c#constructorioc-containercode-contracts

Code Contracts with IoC in Class Constructor Method


I'm new in Code Contracts and I've a question about how to integrate it with IoC. I've tried to use Code Contracts in simple test program (classic consolle project), but now I would to use it in my official projects. The question is: if I've a container that supplies my service interface in the constructor method of a class, how can I use Code Contracts to check the values passed?

The classic scenario could be

[ContractClass(typeof(ArticoliBLLContract))]
public interfare IMyInterface
{
 void method1(int a)
 void method2(string b)
 void method3(bool c)
}


[ContractClassFor(typeof(IArticoliBLL))]
public abstract class MyContractsClass : IMyInterface
{

 public void method1(int a)
 {
  Contract.Requires<ArgumentOutOfRangeException>(a > 0,"a must be > 0");                                                    
 }

 public void method2(string b)
 {
  Contract.Requires<ArgumentOutOfRangeException>(!String.IsNullOrEmpty(b),"b must be not empty");                                    
 }

 public void method3(bool c)
 {
  Contract.Requires<ArgumentOutOfRangeException>(c == true,"c must be true");                                    
 }
}


 public class MyClass : IMyInterface
 {
  private ITFactory _factory = null;
  private IMyDAL _myDAL = null;

  public MyClass(ITFactory factory,IMyDAL myDAL)
  {
    if (factory == null)
      throw new ArgumentNullException("factory");

    if (myDAL == null)
      throw new ArgumentNullException("myDAL");

    _factory = factory; 
    _myDAL = myDAL;
  }

  public void method1(int a)
  {
    a = a*2;
  }

  public void method2(string b)
  {
    b = b + "method2";
  }

  public void method3(bool c)
  {
    c = false;
  } 
 }

In this scenario, where can I check "factory" and "myDAL"? Is there a way to put contracts in the Abstract Class to keep it in the same class?

Thank you!!!


Solution

  • The requirement for constructor parameters is specific to a particular implementation - just like constructors themselves aren't inherited, their required parameters aren't.

    I would express them as contracts within the constructor as normal, but that's all - they shouldn't be part of the abstract class set of contracts. (Consider another concrete subclass which implemented the methods without using those parameters at all. It's an entirely reasonable scenario, and nothing should fail just because you don't have those values.)