I wrote a page that allows me to change my password. The code works and it does everything I want it to do, so I started writing tests. Since I'm not as experienced in Angular testing this had proven to be quite difficult and I can't get passed this error:
TypeError: 'undefined' is not an object (evaluating 'plan.apply')
at /Users/denniegrondelaers/asadventure/myproject-web/src/users/controllers/userPasswordController.js:9
at /Users/denniegrondelaers/asadventure/myproject-web/test/unitTests/specs/users/controllers/userPasswordControllerSpec.js:98
The controller: userPasswordController.js
users.controllers.controller('userPasswordController',
['$scope', 'Session', '$state', 'UserService', 'languages',
function ($scope, Session, $state, UserService, languages) {
$scope.languages = languages;
$scope.password = "";
$scope.notEqual = false;
$scope.isSuccessful = false;
$scope.changePassword = function() {
var pw = {
userId: Session.getCurrentSession().userId,
oldPassword: encrypt($scope.password.oldPassword),
newPassword: encrypt($scope.password.newPassword),
newPasswordRepeat: encrypt($scope.password.newPasswordRepeat)
};
if (pw.newPassword === pw.newPasswordRepeat) {
$scope.notEqual = false;
UserService.setNewPassword(pw).then(function(res) {
$scope.formErrors = undefined;
$scope.isSuccessful = true;
}, function (error) {
$scope.formErrors = error.data;
}
);
} else {
$scope.notEqual = true;
}
};
var encrypt = function (password) {
var encrypted = CryptoJS.md5(password);
return encrypted.toString(CryptoJS.enc.Hex);
};
}
]
);
The service: userService.js
userService.setNewPassword = function (password) {
return $http
.put(EnvironmentConfig.endpointUrl +
"/password/change", password)
};
The test: userPasswordControllerSpec.js
describe('Users', function () {
describe('Controllers', function () {
fdescribe('userPasswordController', function () {
var $scope,
controller,
$q,
willResolve,
mockSession,
mockState,
mockUserService,
mockLanguages;
beforeEach(function () {
module('mysite.users.controllers');
module(function ($provide) {
$provide.value('translateFilter', function (a) {
return a;
});
$provide.value('$state', function (a) {
return a;
});
});
mockSession = {
getCurrentSession: function () {
return {userId: 4};
}
};
mockState = {
params: {
id: 1
},
go: function () {
}
};
mockLanguages = {
getLanguages : function () {
var deferred = $q.defer();
deferred.resolve({
data: [{}]
});
return deferred.promise;
}
};
mockUserService = {
setNewPassword : function () {
var deferred = $q.defer();
if (willResolve) {
deferred.resolve({
data: [{}]
});
}
return deferred.promise;
}
};
inject(function (_$q_, $controller, $rootScope) {
controller = $controller;
$q = _$q_;
$scope = $rootScope.$new();
});
controller('userPasswordController', {$scope: $scope, Session: mockSession, $state: mockState,
UserService: mockUserService, languages: mockLanguages
});
willResolve = true;
});
it('should change password', function () {
spyOn(mockUserService, 'setNewPassword').and.callThrough();
spyOn(mockState, 'go').and.callThrough();
spyOn(mockSession, 'getCurrentSession').and.callFake();
expect(mockUserService.setNewPassword).not.toHaveBeenCalled();
expect($scope.isSubmitable()).not.toBeTruthy();
$scope.compareStoreSelection = function () {
return true;
};
$scope.password = {
oldPassword: "123456",
newPassword: "password",
newPasswordRepeat: "password"
};
expect($scope.isSubmitable()).toBeTruthy();
>>> $scope.changePassword(); <<< LOCATION OF ERROR, line 98
expect(mockUserService.setNewPassword).toHaveBeenCalled();
$scope.$apply();
});
});
});
});
I've marked the line that gives the code in the test.
Anybody any idea how to fix this? A colleague suggested altering my controller code, but I'd like to keep it as it is, since it seems logical that this code shouldn't be altered for testing to work, right?
Aucun commentaire:
Enregistrer un commentaire