在Angular中返回从工厂到控制器的响应

时间:2015-09-25 04:23:10

标签: javascript angularjs

我有一个工厂,它通过api调用请求用户数据:

angular.module('MyApp')
    .factory('UserApi', function($auth,Account){
        return {
            getProfile: function()
                {
                 Account.getProfile()
                    .then(function(response){
                        return response.data; ----> returning json data ok!!
                    });

                }
        }   
});

但是当我在控制器中调用该函数时,它会返回 undefined

myApp.controller('AppCtrl', function($rootScope,$state,$window,$document,$scope,$filter,$resource,cfpLoadingBar,$translate,UserApi){

$scope.user = function(){
        UserApi.getProfile().then(function(data){
            $scope.currentUser = data;
        })
    }
console.log($scope.user()); ----> undefined
});

帐户工厂:

angular.module('MyApp')
    .factory('Account', function($http){
        return {
            getProfile: function(){
                 return $http.get('/api/me');
            }
        }
    });

登录控制台的错误是TypeError: Cannot read property 'then' of undefined

修改

唯一可用的解决方案是将response.data设置为$rootScope.user,其中数据将通过控制器提供。

angular.module('MyApp')
    .factory('UserApi', function($auth,Account,$rootScope){
        return {
            getProfile: function()
                {
                 Account.getProfile()
                    .then(function(response){
                        $rootScope.user = response.data; ----> returning json data ok!!
                    });
                    return $rootScope.user;
                }
        }   
});

3 个答案:

答案 0 :(得分:0)

已编辑

你未定义。这是因为:

  • return
  • 中没有$scope.user
  • 您的console.log($scope.user($scope.user())仅适用于初始时间。
  • UserApi.getProfile()
  • 获取数据有时间延迟
  • 此外,您的代码有一些错误:

我可以建议:

  • 请勿使用console.log($scope.user())初始时间。
  • 或者,您应该在工厂创建时获取所有数据的初始时间。然后,在控制器中使用UserApi.data。(但是,有时间延迟。如果在加载控制器之前请求返回响应,则可能会获得成功数据。)

angular.module('MyApp')
    .factory('UserApi', function ($auth, Account) {
        var data;
        Account.getProfile().then(function (response) {
            data = response.data;
        });
        return {
            data: data
        }
    });

myApp.controller('AppCtrl', function ($rootScope, $state, $window, $document, $scope, $filter, $resource, cfpLoadingBar, $translate, UserApi) {
    console.log(UserApi.data);
});

答案 1 :(得分:0)

您正在尝试在请求成功完成后返回数据。但是,由于这是一个ajax调用,我们不知道它什么时候完成(基本上,在不同的线程上运行)。有两种方法可以解决这个问题。

1 - 只需像这样回复电话。

angular.module('MyApp')
    .factory('UserApi', function($auth,Account){
        return {
            getProfile: function(){
                     return Account.getProfile(); // return call and resolve in controller.                   

                }
        }   
});

2 - 你可以使用promise($ q)

angular.module('MyApp')
    .factory('UserApi', function($auth,Account, $q){
        return {
            getProfile: function(){
                     var deferred = $q.defer();
                     Account.getProfile()
                       .success(function(data){
                           deferred.resolve(data);
                     });                   
                     return deferred.promise; // just return the promise
                }
        }   
});

并且在您的控制器中只有以下内容。

myApp.controller('AppCtrl', function($rootScope,$state,$window,$document,$scope,$filter,$resource,cfpLoadingBar,$translate,UserApi){

    $scope.user = function(){
        UserApi.getProfile().then(function(data){
            $scope.currentUser = data;
            console.log($scope.currentUser);
        });
    }
});

答案 2 :(得分:0)

首先,getProfile方法应该返回一个承诺(不像它在代码中所做的那样未定义):

angular.module('MyApp')
    .factory('UserApi', function($auth,Account){
        return {
            getProfile: function()
                {
                 return Account.getProfile()
                    .then(function(response) {
                        return response.data;
                    });
                }
        }   
});

然后在控制器中你应该使用then回调:

myApp.controller('AppCtrl', function ($rootScope, $state, $window, $document, $scope, $filter, $resource, cfpLoadingBar, $translate, UserApi) {

    $scope.user = function () {
        UserApi.getProfile().then(function (data) {
            $scope.currentUser = data;
            console.log($scope.currentUser);
        })
    };
});

另外,请确保您了解同步代码和异步代码之间的区别,以及console.log($scope.user())在这种情况下没有意义的原因:当您尝试记录时,如果尚未提供响应。相反,您提供了一个在数据到来时调用的回调。