我对单元测试比较陌生,我想知道是否有针对以下问题的内置解决方案。
我想测试一种方法,它一度测量来自硬件的一些输入。
var results = Measurement.MeasureAll();
我当然希望在没有硬件的情况下测试它。有没有办法以某种方式覆盖单位测试范围的Measurement.MeasureAll();返回一些预定义值的方法?
答案 0 :(得分:4)
你会嘲笑依赖。这是你的依赖:
Measurement
什么是Measurement
?它从何而来?为了使代码单元可测试,应该为该代码提供Measurement
。像这样:
public void MethodBeingTested(Measurement measurement)
{
// use Measurement here
}
或许这个:
public class SomeClass
{
private Measurement TheMeasurement { get; set; }
public SomeClass(Measurement theMeasurement)
{
TheMeasurement = theMeasurement;
}
public void MethodBeingTested()
{
// use TheMeasurement here
}
}
然后您的单元测试可以创建假/模拟/存根/等。 Measurement
并将其提供给测试。 (有很多模拟库可以帮助解决这个问题。我个人喜欢Moq和RhinoMocks。)“模拟”版本将由测试定义,以特定和可预测的方式执行。然后它会观察到被测试的代码与模拟完全按照预期的方式进行交互。
现在,一些对象很难被嘲笑。 如果您向我们展示的内容为static
,尤其会出现这种情况。(静态成员会让单位测试变得非常困难。)这是您要包装的地方在可以模拟的可模拟包装器中的这样一个对象。像这样简单:
public interface IMeasurement
{
SomeType MeasureAll();
}
public class MyMeasurement
{
// declare Measurement here? some other context?
public SomeType MeasureAll()
{
return Measurement.MeasureAll();
}
}
这里的想法是,您的业务逻辑将耦合到IMeasurement
,您可以通过它完全控制和模拟/可测试性。然后你可以提供一个包装类的模拟版本(通过使用接口使其变得微不足道),而不必担心模拟实际的依赖。