0

I am trying to return a http get request from a rest api url inside a factory. But it's not returning data but instead the function. When I use console log inside the controller it show the whole function.

MyApp.factory('userFactory', function($http) {

    var factory = [];

    factory.users = function(){
        $http({
            url: '/test/users',
            method: 'GET'
        })
        .then(function successCallback(response) {
            factory.users = response;

        }, function errorCallback(response) {
            factory.users = response;
        });

        return factory.users;
    };

    return factory;

});
2
  • You are using a slightly different method than I use ($http.get), but I think the problem is that you need to return the $http promise. Try factory.users = function() { return $http(... and we can go from there. Commented Sep 30, 2015 at 1:52
  • 1
    you should be returning response.data, but you can't change a function into an object inside the function itself... (i.e. factory.users is a function, and so inside this function, trying to assign factory.users to a different object isn't going to work). Commented Sep 30, 2015 at 1:58

2 Answers 2

1

I do the same thing in my projects. Check out the repo here: https://github.com/ahmadabdul3/mean-flapperNews/tree/master/public/Index/angular

the httpService is my http handler. Then you can look at the postsService, see my getAllPosts function

basically like the comments say, you have to return a promise and handle it in the controller

so you do it like this:

function getAllPosts() {
        httpService.baseGet(httpUrls.posts)
        .then(function(data) {
            angular.copy(data, posts);
            posts.push({title: 'post test', link: '', upvotes: 3, comments: []});
        }, function(data) {
            httpService.handleError(data);
        });
    }

and have the http service do the work:

angular.module('httpService', [])
.factory('httpService', httpService);

httpService.$inject = ['$http', '$q'];

function httpService($http, $q) {
    var serv = this;
    var methods = {
        httpGet : 'GET',
        httpPost : 'POST',
        httpPut : 'PUT',
        httpDelete : 'DELETE'
    };
    function baseGet(url) {
        return $http.get(url).then(
                function (result) {
                    return result.data;
                },
                function (result) {
                    return $q.reject(result);
                }
                );
    }
    function httpWithParams(url, method, data) {

        return $http({
                url: url,
                method: method,
                params: data,
                dataType: "json",
                headers: {
                    "Content-Type": "application/json"
                }
            }).then(
                function (result) {
                    console.log(result.data);
                    return result.data;
                },
                function (result) {
                    return $q.reject(result);
                }
            );
    }
    function handleError(error) {
            console.log(error);
    }

    return {
        baseGet: baseGet,
        httpWithParams: httpWithParams,
        handleError: handleError,
        methods: methods
    }
}
Sign up to request clarification or add additional context in comments.

Comments

1

See $http docs - it returns a promise so you need to handle this accordingly. You also seem to have some conflicts in your variable naming which will not help the issue.

I suggest following johnpapa's angular style guide - and in this case the data services rule. You have most of this already.

You could either handle the promise in the controller like below - or use a setter (getUser / setUsers on factory to share between controllers/concerns).

  MyApp.factory('userFactory', function($http) {
    // Expose public API first, use func notation
      return { 
          getUsers: getUsers,
      };

      function getUsers(){
          return $http.get('/test/users');
      }
 });

 MyApp.controller('UserController', function(userFactory) {
    // bindables up top
    vm.users = [];

    activate();

    //separate activation logic / promise resolution
    function activate(){
        userFactory.getUsers().then(function(users){
          vm.users = users.data;
        });
    }    
});

1 Comment

Got it working by using the code from above. Also have read through some of johnpapa style guide. Very useful thanks!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.