2016-02-08 61 views
1

我正在使用angular和jasmine進行單元測試。

Result Message: Error: [$injector:modulerr] http://errors.angularjs.org/1.4.9/ $injector/modulerr...

單元測試

/// <reference path="../Scripts/_references.js" /> 
/// <reference path="jasmine.js" /> 
/// <reference path="SampleController.js" /> 

describe('Controller Unit Test: ', function() { 
    var scope, ctrl, $timeout; 
    var someServiceMock; 

    beforeEach(function() { 
     module('app'); 
    }); 

    beforeEach(function() { 
     someServiceMock = jasmine.createSpyObj('someService', ['someAsyncCall']); 
     inject(function ($rootScope, $controller, $q, _$timeout_) { 
      scope = $rootScope.$new(); 
      someServiceMock.someAsyncCall.andReturn($q.when('weee')); 
      $timeout = _$timeout_; 
      ctrl = $controller('SampleController', { 
       $scope: scope, 
       someService: someServiceMock 
      }); 
     }); 
    }); 

    it('Controller exists', function() { 
     expect(ctrl).toBeDefined(); 
    }); 
}); 

控制器

var app = angular.module('myApp', []); 
app.controller('SampleController', function ($scope, someService) { 

    //set some properties 
    $scope.foo = 'foo'; 
    $scope.bar = 'bar'; 

    //add a simple function. 
    $scope.test1 = function() { 
     $scope.foo = $scope.foo + '!!!'; 
    }; 

    //set up a $watch. 
    $scope.$watch('bar', function (v) { 
     $scope.baz = v + 'baz'; 
    }); 

    //make a call to an injected service. 
    $scope.test2 = function() { 
     someService.someAsyncCall($scope.foo) 
      .then(function (data) { 
       $scope.fizz = data; 
      }); 
    }; 
}); 

app.factory('someService', function ($timeout, $q) { 
    return { 

     // simple method to do something asynchronously. 
     someAsyncCall: function (x) { 
      var deferred = $q.defer(); 
      $timeout(function() { 
       deferred.resolve(x + '_async'); 
      }, 100); 
      return deferred.promise; 
     } 
    }; 
}); 

最後,我引用文件:

01運行測試時,我收到以下錯誤
/// <reference path="angular.min.js" /> 
/// <reference path="angular-mocks.js" /> 
/// <reference path="angular-animate.min.js" /> 
/// <reference path="angular-sanitize.min.js" /> 
/// <reference path="angular-route.min.js" /> 
/// <reference path="jquery-2.1.1.min.js" /> 
/// <reference path="jquery.unobtrusive-ajax.js" /> 
/// <reference path="jquery.unobtrusive-ajax.min.js" /> 
/// <reference path="jquery.validate.min.js" /> 
/// <reference path="ui-bootstrap-tpls-0.14.3.min.js" /> 
/// <reference path="modernizr-2.8.3.js" /> 

當我在測試中的注入函數中設置一個斷點並運行調試模式時,它將進入它的內核。

+0

您的單元測試文件頂部的引用列表中沒有對您的控制器文件的引用。訂單也很重要,確保它是最後引用的文件。 – Igor

+0

對不起,它在那裏,但我試圖嘗試一些東西。我仍然得到相同的錯誤 – steveareeno

回答

0

試着修改你的測試代碼,我也冒充你的結構,以便你的測試可能更有效一些。對於較小的控制器/測試,這並不重要,但對於更復雜的功能,重置測試集的能力使這更容易。

第1個beforeEach會將$injector注入到您可以用來獲取參考的函數中。這可以在主要describe函數中完成,因爲它們可能不會更改。

第二個beforeEach我嵌套在一個新的describe函數中。然後,您可以創建一組批處理測試,其中每個it都有一個新的/新的控制器實例。

如果$injector爲空或未定義,則意味着腳本未被加載或按錯誤順序加載。爲了更好地解決此問題,您需要查看注入失敗的原因,因爲Angular尚未意識到它,在這種情況下,請評論您的帖子頂部的完整消息/網址,然後我們可以將參考按正確的順序。

控制器的文件

/// <reference path="jquery-2.1.1.min.js" /> 
/// <reference path="angular.min.js" /> 
... rest of your code 

單元測試文件

/// <chutzpah_reference path="angular.min.js"/> 
/// <chutzpah_reference path="angular-mocks.js"/> 
// you might need additional chutzpah_reference but it really depends on your chutzpah configuration found in chutzpah.json 
/// <reference path="jquery-2.1.1.min.js" /> 
/// <reference path="angular.min.js" /> 
/// <reference path="angular-mocks.js" /> 
/// <reference path="jasmine.js" /> 
/// <reference path="SampleController.js" /> 

describe('Controller Unit Test: ', function() { 
    var $rootScope; //, $timeout; 
    var someServiceMock; 

    beforeEach(function() { 
     angular.mock.module("app"); // mock your module 
    }); 

    // setup 
    beforeEach(inject(function ($injector) { 
     someServiceMock = jasmine.createSpyObj('someService', ['someAsyncCall']); 
     someServiceMock.someAsyncCall.andReturn($q.when('weee')); 

     var $rootScope = $injector.get("$rootScope"); 
     // $timeout = $injector.get("$timeout"); // not used anywhere that I can see 
    })); 

    describe('this will executes initial some set of tests on your controller',() => { 
     var scope; 
     var ctrl; 
     beforeEach(inject(function ($controller) { 
      scope = $rootScope.$new(); 
      ctrl = $controller('SampleController', { 
       $scope: scope, 
       someService: someServiceMock}); 
     })); 

     it('Controller exists', function() { 
      expect(scope).toBeDefined(); 
      expect(ctrl).toBeDefined(); 
     }); 
    }); 
}); 

編輯1

更改引用。添加了角度模擬調用。

+0

我將其複製到另一個測試文件和相同的錯誤。當我斷點並將其懸停在範圍和ctrl變量中時,它們是未定義的。無論如何,代碼永遠不會進入注入功能塊。 – steveareeno

+0

@steveareeno - 我更新了代碼。你能否相應地更新你的參考文獻,並打電話給模擬模塊? – Igor

+0

我試過了,甚至完全從控制器和單元測試中刪除了服務ref。如果我在VS 2012中使用chutzpah,它有什麼區別嗎? – steveareeno