【问题标题】:How to spyOn NodeJS module singleton with Jasmine如何使用 Jasmine 监视 NodeJS 模块单例
【发布时间】:2016-11-29 04:53:55
【问题描述】:

我想用 Jasmine 监视一个直接导出方法的模块:

我的模块

module.exports = (arg, arg) => { 
  //do something...
  callAMethod();
  //return
}

茉莉花

spyOn(myModule);
// since I don't have any method to use spyOn(myModule, <method>)

我发现我可以用这个:

//describe..
    var myModule = require('./myModule');

       it...
         myModule = jasmine.createSpy().and.callFake(function() {
           return false;
         }); // <-this should work

         functionBeingTested(..args);

         expect(myModule).toHaveBeenCalled(); /*I get false, even if
                                                it is actually called
                                                in the functionBeingTested*/

我找到的另一个解决方案是 spyOn myModule.prototype 或设置 jasmine.createSpy().and.returnValue(false) 但我都没有成功。

我怎样才能像上面所说的那样使用 spyOn?

【问题讨论】:

    标签: node.js unit-testing jasmine


    【解决方案1】:
    • 我创建了一个简单的 snippet,它模仿了 require js 加载库和调用方法的功能。

    • 我列出了三个间谍,每个都有不同的场景来解释如何 偷窥

    注意:

    • 我没有使用 require.js 本身,而是模仿了它的功能 然而
    • 因为require.js exports module.exports,我们没有 控制 require 调用的功能,因此我们可以 无法在该方法上安装间谍。
    • 请按照每个它的情况进行说明。

    希望这会有所帮助!

        var callAMethod = function() {
          return "Hello";
        }
        var myModule = {};
        myModule.exports = function(name, title) {
         return callAMethod() + " " + title + "." + name;
        }
    
        // Note that this require mimics the actual require.js require methodology, bascially returns the instantiated version of the library to be used.
        var require = function() {
          return myModule.exports;
        }
    
        // some function that uses the require library to load the js and then does something with it.
        var testFunc = function() {
          var myMod = require('abc');
          return myMod("Bruce", "Mr");
        }
    
        describe('test mymodule', function() {
          // This test fails because though you are mocking the instance here and not the actual call.
          it('test that fails', function() {
            var myModuleTest = require('abc');
            myModuleTest = jasmine.createSpy().and.callFake(function() {
              return false;
            });
            var result = testFunc();
            console.log(result);
            expect(result).toBe(false);
          });
          // this test passes since we have hijacked the require attribute itself and then routed its call to return the Boolean true which means that myModule now return the true statement
          it('test that passes', function() {
            require = jasmine.createSpy().and.callFake(function() {
              return function() {
                return true;
              };
            });
            var result = testFunc();
            console.log(result);
            expect(result).toBe(true);
          });
    
          //callAMethod method call from module.exports may not tested since its the require js that does this call and you have no hook into it, however you can directly test the method like this
          it('test callAMethod', function() {
            console.log(myModule.exports("Bruce", "Mr"));
            spyOn(myModule, 'exports').and.returnValue("Hello Mr.Wayne!");
            var testVal = myModule.exports("Bruce", "Mr");
            expect(testVal).toEqual("Hello Mr.Wayne!");
          })
    
    
        });
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-11-08
      • 2016-01-13
      • 2018-08-28
      • 2012-02-18
      • 2013-11-07
      • 2013-01-09
      相关资源
      最近更新 更多