Amelia Earheart Amelia Earheart - 6 months ago 293
Javascript Question

AngularJS error: Provider must return value from $get factory method

What I'm trying to build is a login service.
I have written a factory that I need to be used by every controller. It's for checking whether user is logged in or not. But I'm getting this error:

Provider must return value from $get factory method


I'm very much new to Angular. Here is my index page:

<!DOCTYPE html>
<html ng-app="myApp">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Index Page</title>

<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.2.2/jquery.min.js"></script>
<script src="assets/lib/angular.js"></script>
<script src="assets/lib/angular-route.js"></script>

<script src="app/app.js"></script>
<script src="app/AuthenticationService.js"></script>
</head>
<body>
<div ng-view></div>
</body>
</html>


app.js file:

( function () {

angular.module('myApp', [
'ngRoute',
'ngAnimate',
'myApp.login',
'myApp.home',
'myApp.AuthenticationService'
])
.config(['$routeProvider', function($routeProvider) {
$routeProvider
.when('/login', {
controller: 'LoginController',
templateUrl: 'loginView.html',
controllerAs: 'vm'
})
.when('/home', {
controller: 'HomeController',
templateUrl: 'HomeView.html',
controllerAs: 'vm'
})
.otherwise({
redirectTo: '/login'
});
}]);
})();


And this is the factory that I set up:

(function() {

angular
.module('myApp.AuthenticationService', [])

.factory('AuthService', ["$http", "$location", function($http, $location){
var vm = this;
vm.checkToken = function(token){
var data = {token: token};
$http.post("endpoints/checkToken.php", data).success(function(response){
if (response === "unauthorized"){
console.log("Logged out");
$location.path('/login');
} else {
console.log("Logged In");
return response;
}
}).error(function(error){
$location.path('/login');
})

}

}]);

})();

And this is how I inject it in a controller:

(function() {

angular
.module('myApp.home', [])

.controller('HomeController', function($routeParams,AuthService) {
var vm = this;

//If user is not logged in
var token;
if (localStorage['token']){
token = JSON.parse(localStorage['token']);
} else {
token = "something stupid";
}
AuthService.checkToken(token);

$scope.logout = function(){
var data = {
token: token
}

$http.post('endpoints/logout.php', data).success(function(response){
console.log(response)
localStorage.clear();
$state.go("login");
}).error(function(error){
console.error(error);
})
}

});

})();


Can anyone point out the mistake I made? Thanks in advance.

Answer

In terms of factory you must return an object. Since you're not returning anything, it means that other services/controllers can't use this AuthService service. You need to return return vm; from AuthService service.

(function() {

angular
.module('myApp.AuthenticationService', [])

.factory('AuthService', ["$http", "$location", function($http, $location){
    var vm = this;
    vm.checkToken = function(token){
        var data = {token: token};
        $http.post("endpoints/checkToken.php", data).success(function(response){
            if (response === "unauthorized"){
                console.log("Logged out");
                $location.path('/login');
            } else {
                console.log("Logged In");
                return response;
            }
        }).error(function(error){
            $location.path('/login');
        })

    }
   return vm;
}]);

})();

The service factory function generates the single object or function that represents the service to the rest of the application. The object or function returned by the service is injected into any component (controller, service, filter or directive) that specifies a dependency on the service.

Comments