使用Jasmine监视Backbone.js查看函数

时间:2012-12-27 15:04:00

标签: backbone.js jasmine

我正在尝试编写一个Jasmine规范,以验证在将模型添加到视图集合时调用视图的函数。

在视图的初始化函数中我做

this.collection.on('add', this.fooAdded, this);

在我的Jasmine规范中,我正在做:

describe('Foo View', function() {
   it('should call fooAdded when a Foo is added', function() {
      var view = new FooView({collection: new FooCollection()});
      spyOn(view, 'fooAdded').andCallThrough();
      view.delegateEvents();
      view.collection.add({name: 'foo'});
      expect(view.fooAdded).toHaveBeenCalled();
   });
});

我的fooAdded()实现会将某些内容记录到控制台,所以我知道它正在被调用。然而,间谍没有看到fooAdded()已被调用。

查看我的jsFiddle

2 个答案:

答案 0 :(得分:4)

你的问题是spyOn用一个新的包装函数替换了spied on函数,但是在使用该函数后你将它替换为。当你调用spyOn(view, 'fooAdded')来附加你的间谍时,对原始fooAdded的引用已经存在于集合的监听器列表中,因此监视该回调为时已晚。

如果您在实例化视图之前监视视图原型中的fooAdded

spyOn(FooView.prototype, 'fooAdded');
var view = new FooView(...);
view.delegateEvents();
//...
然后事情应该更好。演示:http://jsfiddle.net/m5Baw/1/(感谢amiuhle更新演示中的Jasmine链接。)

顺便说一句,我觉得你的观点有些奇怪,你不应该在视图代码之外view.delegateEvents(),所以你可能想要仔细研究一下。

答案 1 :(得分:2)

我即将回应,而“mu太短”正是关键。证明您的间谍没有注册的第一件事是使用以下代码而不是您的spyOn(view, 'fooAdded').andCallThrough();

spyOn(FooView.prototype, 'fooAdded').andCallFake(function(){
           console.log('fake "fooAdded" called');
        });

由于fooAdded已经在集合侦听器中注册,因此永远不会调用此方法。这是更新的jsFiddle