在C#中使用起订量嘲讽 [英] Mocking using Moq in c#

查看:121
本文介绍了在C#中使用起订量嘲讽的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有以下代码:

 公共接口IProductDataAccess 
{
布尔CreateProduct(产品展示新品推荐);
}



ProductDataAccess 工具该接口。

 公共类ProductBusiness 
{
公共BOOL CreateProduct(产品展示新品推荐)
{
IProductDataAccess PDA =新ProductDataAccess();
布尔结果= pda.CreateProduct(新品展示);
返回结果;
}
}

在这种情况下,如何为创建单元测试 CreateProduct 以嘲讽 IProductDataAccess 接口方法?我想在 ProductBusiness IProductDataAccess 的一个公网实例和使用初始化的模拟< IProductDataAccess> ; 对象,但它不是暴露在UI层的数据访问一个很好的做法。任何一个能帮助我吗?


解决方案

经典的例子说明如何,如果你不能单元测试特定组件,重构组件<! / p>

这就是爱了任何模拟框架强制你做 - 写去耦代码



在你的榜样中, ProductBusiness 类是非常紧密耦合与 ProductDataAccess 。你可以用它(最喜欢的答案建议)依赖注入脱钩。通过这样做,你最终会取决于 IProductDataAccess 抽象比任何具体实施了。



另外一点要注意,当你写测试/规格为业务层,你通常要测试的行为,而不是国家。因此,尽管你可以有断言验证,如果真被退回,您的测试应该真正测试如果用起订量,我们实际使用最小起订量的.VerifyAPI执行。设定预期的数据访问调用



尝试添加在那里你期望一个抛出异常行为检测的数据访问层(使用.ThrowsAPI),并检查是否需要在业务层的任何特殊处理。



像凯文表明,有它看起来像ProductBusiness:

 公开类ProductBusiness 
{
私人只读IProductDataAccess _productDataAccess;

公共ProductBusiness(IProductDataAccess productDataAccess)
{
_productDataAccess = productDataAccess;
}

公共BOOL CreateProduct(产品展示新品推荐)
{
布尔结果= _productDataAccess.CreateProduct(新品展示);
返回结果;
}
}

和使用任何的xUnit测试框架编写测试作为

  VAR mockDataAccess =新的模拟< IProductDataAccess>(); 
mockDataAccess.Setup(M = GT; m.CreateProduct(It.IsAny<产品及GT;()))返回(真)。
变种productBusiness =新ProductBusiness(mockDataAccess.Object);
//行为进行测试


I have the following code:

public interface IProductDataAccess
{
    bool CreateProduct(Product newProduct);
}

Class ProductDataAccess implements that interface.

public class ProductBusiness
{
    public bool CreateProduct(Product newProduct)
    {
        IProductDataAccess pda = new ProductDataAccess();
        bool result = pda.CreateProduct(newProduct);
        return result;
    }
}

In this case, how to create unit test for CreateProduct method by mocking the IProductDataAccess interface? I thought of having an public instance of IProductDataAccess within ProductBusiness and initialize it using Mock<IProductDataAccess> object but it is not a good practice to expose the data access to the UI layer. Can any one help me?

解决方案

Classic example which shows how if you cannot unit test a particular component, REFACTOR the component!

This is where is love what any mocking framework enforces you to do - write decoupled code.

In your example, the ProductBusiness class is very tightly coupled with the ProductDataAccess. You could decouple it using (like most of the answers suggest) dependency injection. By doing so, you would end up depending on the IProductDataAccess abstraction than any concrete implementation of it.

Another point to note, when you are writing tests/specifications for the business layer, you would typically want to test the "behavior" and not the "state". So, though you could have asserts that verify if "true" was returned, your tests should really test if the expected data access calls that were set using MOQ we actually executed using the ".Verify" API of MOQ.

Try adding behavior tests where you expect an exception to be thrown(using the ".Throws" API) by the data access layer and check if you need any special handling at the business layer.

Like Kevin suggests, have the ProductBusiness which looks like:

public class ProductBusiness
{
  private readonly IProductDataAccess  _productDataAccess;

  public ProductBusiness(IProductDataAccess productDataAccess)
  {
      _productDataAccess = productDataAccess;
  }

  public bool CreateProduct(Product newProduct)
  {
    bool result=_productDataAccess.CreateProduct(newProduct);
    return result;
  }
}

and use any xunit testing framework to write the test as:

 var mockDataAccess = new Mock<IProductDataAccess>();
 mockDataAccess.Setup(m => m.CreateProduct(It.IsAny<Product>())).Returns(true);
 var productBusiness = new ProductBusiness(mockDataAccess.Object);
 //behavior to be tested

这篇关于在C#中使用起订量嘲讽的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆