模拟设置了一个没有集合的属性

时间:2014-02-14 16:56:07

标签: c# mocking

大家比我聪明:-)我有另一个需要生成抽象类的应用程序,并且由于测试目的很难调试。因此我创建了一个包装器,现在可以在Visual Studio中定义我的抽象类(而不是本机应用程序)

但是,本机应用程序期望公共abstract [obj type]值只有get;方法,如果我放入一套;,应用程序将炸弹。有没有办法使用Reflection或Mock为此字段设置字段,而没有设置方法?

//simplified class
public abstract class GetEUserAndDetails : [app specific interfaces]
{
      public abstract Metastorm.Runtime.Types.Text paramFullNameLike
      {
            get;
            set; //note: If i have this here, it will fail in Metastorm
      }
      public System.Data.DataSet Read()
      {
            //do something
      }
}

并且在Main()中它是一个c#winform,我有

Mock<Metastorm.Runtime.Models.MySampleProject.GetEUserAndDetails> mockMyBO = new Mock<Metastorm.Runtime.Models.MySampleProject.GetEUserAndDetails>() { CallBase = true };

//using reflection
foreach (PropertyInfo pi in mockMyBO.Object.GetType().GetProperties())
{ 
     //simplified again, another form getting parameters and such
     pi.SetValue(mockMyBO.Object, form.myTextParam, null);
}

如果我没有set方法,pi.SetValue()行将失败,但如果我这样做,它将在本机应用程序中失败。 (注意:我使用相同的测试工具来测试所有实现Read()方法的抽象类,并且需要测试它是否正在提取正确的数据,但每个类的参数都不同。

很抱歉,如果我的代码不好,我无法正确格式化,如果我使用错误的条款,也请耐心等待。我无论如何都不是专家,只是危险。我只是生活在离开集合;暂时排队并在复制/粘贴到主应用程序之前手动将其删除,但是当有很多参数时,我想找到另一种方法来执行此操作。

1 个答案:

答案 0 :(得分:0)

如果我理解你的场景,你实际上想要在抽象类中测试代码,而不是模拟它。

考虑到这一点,我认为在这种情况下最简单的方法就是在您的测试中创建一个子类,它将从您的基类继承,并实现您能够测试基类所需的一切。

如:

public class GetUserAndDetailsImplementation : GetEUserAndDetails 
{
    private Metastorm.Runtime.Types.Text _paramFullNameLike;

    public override Metastorm.Runtime.Types.Text paramFullNameLike
    {
        get { return _paramFullNameLike; }
    }

    public void SetParamFullNameLike(Metastorm.Runtime.Types.Text text)
    {
        _paramFullNameLike = text;
    }
}

您可以使用该类作为测试的入口点。

现在,如果您真的想使用模拟器,您是否尝试过以下操作?

var mock = new Mock<GetEUserAndDetails> { CallBase = true };
mock.SetupGet(x => x.paramFullNameLike).Returns(<some value>);