什么时候监视在单元测试期间有用的方法?

时间:2015-04-12 22:25:05

标签: javascript unit-testing jasmine

使用Jasmine可以使用spyOn种方法,但我不清楚它何时会有用。我的理解是单元测试不应该关注实现细节和测试方法是否是实现细节。

我可能想到的一个地方是监视scope.$broadcast(Angular)等,但是这又是实现细节,并且不确定单元测试是否应该打扰代码如何工作,只要它给出了预期结果

显然有充分的理由使用spyOn那么什么是使用它的好地方?

2 个答案:

答案 0 :(得分:0)

你所描述的spyOn在测试中更常被称为MOCK,虽​​然更清楚它允许2次操作:

  1. 通过createSpy为这个方法创建一个新的实现(这是经典的模拟)

  2. 通过spyOn检测现有方法(这样可以查看方法是否被调用,以及args,返回值等)。

  3. 可能是单元测试中最常用的技术。当您测试一个代码单元时,您经常会发现其他代码单元存在依赖关系,并且这些依赖关系具有自己的依赖关系等。如果您尝试测试所有内容,最终会得到模块/ UI测试,这是昂贵的,难以维护(它们仍然有价值,但你想尽可能少)

    这就是模拟的用武之地。想象一下,您的单位会调用REST服务来获取某些数据。您不希望在单元测试中依赖服务。因此,您模拟调用服务的方法,并提供自己的实现,只返回一些数据。想检查您的设备是否处理REST错误?让你的模拟返回错误。等。

    知道您的代码是否实际调用另一个代码单元有时会很有用 - 想象您要确保代码正确调用日志记录模块。只是模拟(spyOn)记录模块并声明它用适当的参数调用了X次。

答案 1 :(得分:0)

你可以窥探功能,然后你就可以断言一些事情 关于它。你可以检查它是否被调用,它有什么参数,如果它 返回了一些东西,甚至还有多少次! 间谍在编写测试时非常有用,所以我将解释如何 在这里使用最常见的。

        // This is our SUT (Subject under test)
        function Post(rest) {
          this.rest = rest; 
         rest.init();
        }

我们这里有我们的SUT,它是一个Post构造函数。它使用RestService来  拿东西。我们的帖子会将所有Rest工作委托给RestService 当我们创建一个新的Post对象时,它将被初始化。我们开始测试了  它一步一步:

    `describe('Posts', function() {
      var rest, post;
      beforeEach(function() {
        rest = new RestService();
        post = new Post(rest);
      });
    });`

这里没什么新东西。由于我们在每次测试中都需要两个实例, 我们将初始化放在beforeEach上,这样我们每个都会有一个新实例 时间。  在创建帖子后,我们初始化RestService。我们想测试一下,如何  我们可以这样做吗?:

    `it('will initialize the rest service upon creation', function() {
      spyOn(rest, 'init');
      post = new Post(rest);
      expect(rest.init).toHaveBeenCalled();
    });`

我们希望确保在创建新的时调用静态init 发布对象。为此,我们使用jasmine spyOn函数。第一个参数是 我们想要放置间谍的对象,第二个参数是一个字符串 代表间谍的功能。在这种情况下,我们想监视函数init 在间谍对象上。然后我们只需要创建一个将调用的新Post对象 那个init函数。最后一部分是断言rest.init已经存在 调用。容易吗?这里重要的是你间谍的时候 函数,从不调用真正的函数。所以这里rest.init实际上并没有 运行