2012-01-24 3 views
4

У меня есть сложный класс javascript, который имеет много функций, многие из которых будут генерировать исключения, если они вызывается за пределами производственной среды. Мне нужно передать макеты экземпляров этого класса в конструктор другого класса в моих тестах, однако я не хочу, чтобы какие-либо из функций сложных классов действительно вызывались. То, что я хотел бы сделать, это иметь поддельный объект, который имеет все функции и свойства сложного класса, но для всех функций просто быть шпионами жасмина, которые ничего не делают.Любой способ отслеживать весь экземпляр с помощью Jasmine

В основном я хочу, чтобы быть в состоянии сделать

var fakeComplexClass = createFakeObject(ComplexClass); 

var testInstanceOfSimpleClass = new SimpleClass(fakeComplexClass); 

И будьте уверены, что если testInstanceOfSimpleClass вызывает какой-либо из функций fakeComplexClass они будут шпионы и, таким образом, не врезаться мои тесты.

я мог бы сделать что-то вроде

var fakeComplexClass = { function1() {};, function2() {}; ... } 

но есть много функций, и у меня есть несколько различных сложные классам мне нужно проверить так просто легкий способ в основном следить за каждую функцию в классе, что Мне нужно. \

У Jasmine есть createSpyObj, но для этого требуется передать ему ряд функций. Я не хочу поддерживать этот массив в своих тестах, если мне приходится добавлять или удалять функции из сложного класса, поэтому мне бы хотелось что-то, что можно просто шпионить за каждой функцией, которая есть.

Заранее спасибо.

ответ

0

Возьмите взгляд на SinonJS, он позволяет вам stub весь объект:

var stub = sinon.stub(obj); заглушек все методы объекта.

+0

Спасибо! Это делает трюк :) – asutherland

1

Я создал небольшую библиотеку, которая работает с жасминовым узлом.

использование:

var MyClass = function (param) { 
     this.initialize(param); 
    }; 
    MyClass.prototype.initialize = function (param) { 
     if (param != "expectedParam") 
      throw new TypeError(); 
    }; 

    var mock1 = jasmine.createStub(MyClass, ["*"]); 
    expect(mock1.constructor).toHaveBeenCalled(); 
    expect(mock1.initialize).not.toHaveBeenCalled(); 

    var mock2 = jasmine.createStub(MyClass, ["initialize"], ["expectedParam"]); 
    expect(mock2.initialize).toHaveBeenCalled(); 
    mock2.initialize.andCallThrough(); 
    expect(mock2.initialize).toThrow(new TypeError()); 

Lib:

jasmine.createStub = function (cls, methods, args) { 
    if (!(cls instanceof Function)) 
     throw new TypeError("Invalid class param."); 

    var mockClass = function() { 
     this.constructor.apply(this, args || []); 
    }; 

    mockClass.prototype = Object.create(cls.prototype); 
    mockClass.prototype.constructor = cls; 

    var wrap = function (method) { 
     if (!mockClass.prototype[method] instanceof Function) 
      throw new TypeError("Cannot mock " + method + " it's not a function."); 
     jasmine.getEnv().currentSpec.spyOn(mockClass.prototype, method); 
    }; 

    if (methods) { 
     if (!(methods instanceof Array)) 
      methods = [methods]; 
     if (methods.length == 1 && methods[0] == "*") 
      for (var property in mockClass.prototype) { 
       if (mockClass.prototype[property] instanceof Function) 
        wrap(property); 
      } 
     else 
      for (var i = 0; i < methods.length; ++i) { 
       var method = methods[i]; 
       wrap(method); 
      } 
    } 

    return new mockClass(); 
}; 

Я думаю, что эта строка не будет работать с жасмином в браузере, но не проверял:

jasmine.getEnv().currentSpec.spyOn(mockClass.prototype, method); 

Как-то мой jasmine- узел не имеет метода жасмина.spyOn ...

Смежные вопросы