如何使用Jasmine模拟JQuery?

时间:2011-10-12 15:22:12

标签: javascript jquery tdd jasmine

如何测试某个JQuery选择器是否已使用Jasmine执行?我正在尝试执行以下操作:

spyOn($.fn, 'init').andCallThrough(); 
// my code
expect($.init).toHaveBeenCalled();

但是在此次通话结束后,$('div')会返回Object { selector="div", context=document, NaN=div.spec, more...},但必须返回($.fn.init('div')确实会返回):[div.jasmine_reporter, div.banner, div.logo, 4 more...]。由于JQuery对象不再可用,因此这些东西自然会破坏代码。

示例:

假设我想测试已经调用了JQuery选择器,我写道:

    it('tests', function() {
        spyOn($.fn, 'init').andCallThrough();
        $('html');
        expect($.init).toHaveBeenCalled();
    });

这导致来自Jasmine的错误:Error: Expected a spy, but got undefined.。然后我在$('html')行的FireBug中设置一个断点,当我到达那里并尝试观察$('html')的值是什么时,我得到:

Object { selector="html", context=document, NaN=html, more...}

如果我发表评论spyOn,该行$('html')评估为:

[html]

我期望看到spyOn也是如此。

1 个答案:

答案 0 :(得分:3)

看起来Jasmine通过用包装版本替换spied-on对象看起来像间谍的东西,这似乎搞乱了jQuery作为一个整体,因为(来自jQuery源代码):

  

// jQuery对象实际上只是init构造函数'enhanced'

我建议你试图窥探一下init使用的一个函数,特别是“merge”。如果你看一下jQuery代码,你会发现任何HTML => DOM的东西最终会通过合并调用返回:

return jQuery.merge( this, selector );

(如果您正在查看jQuery 1.5.1的源代码,那就是第152行)。

通过监视合并,您应该能够测试您正在测试的任何内容,而不会无意中替换jQuery的内容。