Injecting Mock service in AngularJS/ Jasmine
Solution 1
Try get the service using $injector
.
beforeEach(angular.mock.inject(function($rootScope, $http, $location, $timeout, configService, $controller, $injector){
scope = $rootScope.$new();
http = $http;
location = $location;
timeout = $timeout;
service = $injector.get('configService'); //not sure the name, you may try 'ConfigService' as well.
$controller('configCtrl', {$scope: scope, $http: http, $location: location, $timeout: timeout, configService: service});
}));
Link to Demo.
Solution 2
Nice answer from zsong, but that code can be updated further by removing configService
from angular.mock.inject()
as it is not necessary.
Another possibility is to write your test in TypeScript (and use Jasmine type definitions), which is a cleaner way to do it. In that case, your test will look like this:
/// <reference path="typings/jasmine/jasmine.d.ts" />
describe('ConfigCtrl', () => {
var configCtrl, scope, http, location, timeout, configServiceFake;
beforeEach(angular.mock.module('busybee'));
beforeEach(angular.mock.inject(($rootScope, $http, $location, $timeout, configService) => {
scope = $rootScope.$new();
http = $http;
location = $location;
timeout = $timeout;
configServiceFake = configService;
configCtrl = new game.ConfigCtrl(scope, http, location, timeout, configServiceFake);
}));
it('should have text = "constructor"', () => {
expect(true).toBe(true);
});
});
![pichsenmeister](https://i.stack.imgur.com/I7l7D.jpg?s=256&g=1)
pichsenmeister
Updated on July 09, 2022Comments
-
pichsenmeister almost 2 years
I'm using jasmine to test my controllers, which I wrote in TypeScript. My unit tests are in plain javascript. I'm getting an error when I test my controller, where I want to inject a mock service.
This is how my test looks:
'use strict'; describe('ConfigCtrl', function(){ var scope, http, location, timeout, $httpBackend, service; beforeEach(angular.mock.module('busybee')); beforeEach(angular.mock.inject(function($rootScope, $http, $location, $timeout, configService, $controller){ scope = $rootScope.$new(); http = $http; location = $location; timeout = $timeout; service = configService; $controller('configCtrl', {$scope: scope, $http: http, $location: location, $timeout: timeout, configService: service}); })); it('should have text = "constructor"', function(){ expect(true).toBe(true); }); });
My app.ts:
module game { 'use strict'; var busybee = angular.module('busybee', []); busybee.controller('configCtrl', ConfigCtrl); busybee.service('configService', ConfigService); ... ... }
and my TypeScript controller:
module game { 'use strict'; export class ConfigCtrl { static $inject: string[] = ['$scope', '$http', '$location', '$timeout', 'configService']; constructor($scope: ng.IScope, $http: ng.IHttpService, $location: ng.ILocationService, $timeout: ng.ITimeoutService, configService: game.ConfigService) { //any code here } } }
When running karma, I get the following error:
Chrome 28.0.1500 (Linux) ConfigCtrl should have text = "constructor" FAILED TypeError: Cannot read property 'prototype' of undefined at Object.instantiate (/home/david/git/busybee2-client/js/libs/angular/angular.min.js:28:283) at Object.<anonymous> (/home/david/git/busybee2-client/js/libs/angular/angular.min.js:28:494) at Object.d [as invoke] (/home/david/git/busybee2-client/js/libs/angular/angular.min.js:28:174) at /home/david/git/busybee2-client/js/libs/angular/angular.min.js:29:339 at c (/home/david/git/busybee2-client/js/libs/angular/angular.min.js:27:13) at Object.d [as invoke] (/home/david/git/busybee2-client/js/libs/angular/angular.min.js:27:147) at workFn (/home/david/git/busybee2-client/js/libs/angular/angular-mocks.js:1778:20) Error: Declaration Location at Object.window.jasmine.window.inject.angular.mock.inject [as inject] (/home/david/git/busybee2-client/js/libs/angular/angular-mocks.js:1764:25) at null.<anonymous> (/home/david/git/busybee2-client/js/test/ConfigCtrlSpecs.js:9:29) at /home/david/git/busybee2-client/js/test/ConfigCtrlSpecs.js:3:1 Chrome 28.0.1500 (Linux): Executed 1 of 1 (1 FAILED) ERROR (0.329 secs / 0.032 secs)
It seems, there's a problem injecting the
configService
, but I don't have an idea why.EDIT: added a jsfiddle http://jsfiddle.net/Q552U/6/
UPDATE: It seems it was a problem for jasmine having the compiled javascript of the TypeScript classes in different files. Compiling the TypeScript files to a single .js file (
tsc --out dest.js source.ts
), does it for me. -
Braulio about 7 yearsLink to Demo throws a 404