Backbone - тестирование простой модели с использованием Jasmine приводит к TypeError - PullRequest
0 голосов
/ 17 декабря 2011

Я пытался узнать, как тестировать приложение на основе Backbone с помощью Jasmine.Для этого я взял здесь некоторый пример кода: http://msdn.microsoft.com/en-us/scriptjunkie/hh377172.

    Photo = new Backbone.Model.extend({
        defaults:{
            title: 'Another photo!',
            tags:  ['untagged'],
            location: 'home',
            src: 'placeholder.jpg'
        },
        initialize: function(){
            console.log('this model has been initialized');
            this.bind("change:title", function(){
                var title = this.get("title");
                console.log("My title has been changed to.." + title);
            });
        },

        setTitle: function(newTitle){
            this.set({ title: newTitle });
        }
    });

Затем написал тестовую спецификацию следующим образом:

    describe("Photo Model", function() {
        it("verifies title", function() {
        var myPhoto = new Photo();
        myPhoto.set({ title: "On the beach" });   
        expect(myPhoto.get("title"))
            .toEqual("On the beach");
        });
    });

Во время его выполнения проверка завершается с TypeError

    TypeError: Object [object Object] has no method 'apply'
        at new <anonymous> (http://localhost:88/backbone/WebClient-Backbone2/js/backbone.js:1103:41)
        at [object Object].<anonymous> (http://localhost:88/backbone/WebClient-Backbone2/test/spec.js:28:16)
        at [object Object].execute (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:1001:15)
        at [object Object].next_ (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:1790:31)
        at [object Object].start (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:1743:8)
        at [object Object].execute (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:2070:14)
        at [object Object].next_ (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:1790:31)
        at [object Object].start (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:1743:8)
        at [object Object].execute (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:2215:14)
        at [object Object].next_ (http://localhost:88/backbone/WebClient-Backbone2/test/lib/jasmine/jasmine.js:1790:31)     

Ответы [ 3 ]

8 голосов
/ 20 декабря 2011

Как уже упоминалось в комментариях, я узнал, что это связано с «новым» в определении модели.

Итак, после изменения

    var Photo = new Backbone.Model.extend({

на

    var Photo = Backbone.Model.extend({

Ошибка исчезла.

2 голосов
/ 29 марта 2012

Здесь есть хороший набор руководств для тестирования основанного на магистрали приложения с Jasmine: http://tinnedfruit.com/2011/03/03/testing-backbone-apps-with-jasmine-sinon.html

1 голос
/ 17 декабря 2011

Фрагмент кода ниже, вероятно, является виновником.

this.bind("change:title", function(){
  var title = this.get("title");
  console.log("My title has been changed to.." + title);
});

В Javascript контекст области действия ключевого слова this основан на функции, в которой он находится. Так как this находится внутри анонимной функции (this.bind ("change: title", function () ), затем this изменил область действия.

Простое решение - использовать замыкание для установки this на другую переменную вне анонимной функции, а затем вы можете использовать переменную внутри анонимной функции.

Показ примера кода, вероятно, будет лучшеобъясните это. Обновите метод инициализации следующим образом.

    initialize: function(){
        console.log('this model has been initialized');
        var self = this;
        this.bind("change:title", function(){
            var title = self.get("title");
            console.log("My title has been changed to.." + title);
        });
    },

У вас также будет такая же проблема в методе setTitle () . Вам нужно будет добавить эту строку кода вметод initialize () для правильной установки контекста this .

_.bindAll(this, "setTitle");
...