简体   繁体   English

Angular.js单元测试-麻烦模拟$ window

[英]Angular.js unit testing - trouble mocking $window

I made a simple Angular service to interact with local storage. 我做了一个简单的Angular服务来与本地存储进行交互。 It has a has method that returns true/false, depending on if the key exists in local storage. 它具有一个has方法,该方法返回true / false,具体取决于密钥是否在本地存储中。

angular.module("jbLocalStorage", [])
.service("localStorageService", ["$window", function($window){

  this.has = function(key){
    console.log($window); //added to see what $window is referencing in unit test
    if ($window.localStorage.getItem(key) !== null){
      return true;
    } else {
      return false;
    }
  };
}]);

I'm having trouble mocking out $window in my unit test. 我在单元测试中无法模拟出$ window。 The unit test still seems to be accessing the global window object and not accessing the mock. 单元测试似乎仍在访问全局窗口对象,而不在访问模拟。

Here is my unit test for this service. 这是我对该服务的单元测试。 I tried to create a mock $window object, with a getItem function. 我试图用getItem函数创建一个模拟的$window对象。

describe("Has function", function(){
  var localStorageService;

  beforeEach(module('jbLocalStorage'), function($provide){
    $provide.value('$window', {
      localStorage : {
        getItem : function(key){
          if (key === "shape") {return "triangle";} else {return null;}
        },
      },
    });
  });

  beforeEach(inject(function(_localStorageService_){
    localStorageService = _localStorageService_;
  }));

  it("should return true if key is found in local storage", function(){
    expect(localStorageService.has("shape")).toEqual(true);
  });
});

My test fails, because the test seems to look at the global window object and doesn't find "shape", instead of looking in the mock and finding "shape". 我的测试失败了,因为该测试似乎在查看全局window对象并且未找到“形状”,而不是在模拟中查找“形状”。

I know it's doing this, because the console.log line in the service shows that it's still referencing the global window object, not the mock. 我知道它正在这样做,因为服务中的console.log行显示它仍在引用全局window对象,而不是模拟对象。

What am I doing wrong? 我究竟做错了什么? Why is my mock not working? 为什么我的模拟游戏不起作用?

I've done something similar and gotten it working. 我做了类似的事情,并使它起作用。 After reviewing my code I believe I have a solution for you. 查看我的代码后,我相信我为您提供了解决方案。

I think you need to call $provide before you call module('jbLocalStorage') . 我认为您需要在调用module('jbLocalStorage')之前先调用$provide I believe that what is happening is that the $window service is being injected into your code by the module call, then you are modifying the value after it has already been injected. 我相信正在发生的事情是$window服务正在通过module调用注入到您的代码中,然后您已经在注入后修改了该值。

So this should work: 所以这应该工作:

beforeEach(function() {
    module(function($provide) {
        $provide.value('$window', {
            localStorage : {
                getItem : function(key){
                    if (key === "shape") {return "triangle";} else {return null;}
                },
            },
        });
    });
    module('jbLocalStorage');
});

The $provide should be injected into the module function. $ provide应该被注入到模块函数中。

See fiddle here - http://jsfiddle.net/eitanp461/bvsp41yz/ 在这里看到小提琴-http: //jsfiddle.net/eitanp461/bvsp41yz/

describe("Has function", function(){
  var localStorageService;

  beforeEach(module('jbLocalStorage', function($provide){
    $provide.value('$window', {
      localStorage : {
        getItem : function(key){
          if (key === "shape") {return "triangle";} else {return null;}
        },
      },
    });
  }));

  beforeEach(inject(function(_localStorageService_){
    localStorageService = _localStorageService_;
  }));

  it("should return true if key is found in local storage", function(){
    expect(localStorageService.has("shape")).toEqual(true);
    expect(localStorageService.has("wat?")).toBeFalsy();
  });
});

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM