Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Unit testing 如何对亚音速延迟加载特性进行单元测试?_Unit Testing_Orm_Subsonic_Tdd - Fatal编程技术网

Unit testing 如何对亚音速延迟加载特性进行单元测试?

Unit testing 如何对亚音速延迟加载特性进行单元测试?,unit-testing,orm,subsonic,tdd,Unit Testing,Orm,Subsonic,Tdd,假设我有以下要测试的函数: public void CancelOrder(Order order) { order.Status = "Cancelled"; _emailService.SendEmail(order.User.Email, "Your order has been cancelled!"); } 现在,Order类是一个亚音速生成的类,它的用户属性是延迟加载的,这意味着当我调用Order.User.Email时,它实际上运行一个SQL语句来获取用户 如果

假设我有以下要测试的函数:

public void CancelOrder(Order order)
{
    order.Status = "Cancelled";

    _emailService.SendEmail(order.User.Email, "Your order has been cancelled!");
}
现在,Order类是一个亚音速生成的类,它的用户属性是延迟加载的,这意味着当我调用Order.User.Email时,它实际上运行一个SQL语句来获取用户

如果我想对它进行单元测试,我会遇到一些问题,因为我不想让我的单元测试影响我的数据库

我当前的解决方案是重构CancelOrder函数,使其如下所示:

public void CancelOrder(Order order)
{
    order.Status = "Cancelled";

    User user = _userRepository.GetByUserID(order.UserID);

    _emailService.SendEmail(user.Email, "Your order has been cancelled!");
}
然后我可以取消_userRepository.GetUserByID()调用以返回硬编码的用户对象


这是最好的方法吗?我想您可能会认为第二个实现更干净,因为所有数据访问都是通过存储库完成的,而不是隐藏在属性中。

定义您自己的类似顺序的接口,该接口提供您需要的基本功能,并将其用作CancelOrder方法的参数类型:

interface Order {
  public void Status(...); // or property
  public string UserEmail():
} 
然后为该接口创建一个委托实现,例如subsnicorder,该接口调用数据库。在测试中使用存根实现。我意识到您可能需要一个更丰富的订单界面模型;这只是一个例子


如果需要,可以对电子邮件服务进行同样的操作(可能通过构造函数或服务定位器进行依赖注入)。

为什么不希望单元测试访问数据库?如果您使用MBUnit编写测试用例,您可以使用RollBack属性标记单元测试,对数据库的任何更改都将回滚

我一直喜欢编写面向业务层的单元测试用例,但实际上需要ping数据库,以便单元测试与应用程序本身将使用的内容最为相似