backbone.js click event spy is not getting called using jasmine.js and sinon.js

前端 未结 3 1031
无人及你
无人及你 2020-12-28 16:34

I am trying to test a button click using backbone.js, jasmine.js and sinon.js. But the following test case fails. I am using a spy to track whether it is getting called or n

3条回答
  •  情话喂你
    2020-12-28 16:48

    There are some problems with your approach. First you spy on your class you wanna test, with is not the way a unit test should work cause you test the inner logic of your class and not its behavior. Second, and thats the reason why your test fail, you dont have attached your views el into the DOM. So either you attache your el to the DOM or fire the click event directly to the el: $('#add_new_task', this.view.el).click().

    Btw. backbones way to create element and bind events makes it hard to write good unit tests cause you be forced to work with the DOM and jquery. A better way to write testable code would be to always pass all dependencies in to the constructor and dont create new instances in your code cause its hard to test these objects. So in your case it would be much easier to inject the el object in the constructor as a jquery object and at the events manually. Doing it this way you can test you class without any dependencies to the DOM or jquery.

    So in your case the constructor would look like this:

    initialize: function(){
       this.el.click(_.bind( this, 'addTask'));
    }
    

    And your test:

    var el = {click: function(){}};
    spyOn( el, 'click');
    new T.views.NewTaskView({el: el});
    expect(el.click).toHaveBeenCalled(); //test the click event was bind
    //call the function that was bind to the click event, 
    //which is the same as trigger the event on a real DOM object
    el.click.mostRecentCall.args[0]() 
    

    After all you have to decide what approach will fit your needs. Leaner code with backbones helpers or better testable code with less dependencies to jquery, DOM and backbone.

提交回复
热议问题