等待$ http.get在调用服务时完成

时间:2016-10-05 04:56:02

标签: angularjs

我遇到一个问题,即控制器调用服务函数getMyList但myLists尚未填充,因为$ http调用需要一些时间才能完成。

如何解决此问题?

这是我的代码段:

服务

app.factory('myService', function($http) {
    var myList = [];

    $http.get("http://myService/json.data").then(function (resp) {
        myLists = resp.data;
    });

    return {
        getMyList: function (name) {
            for (var i = 0; i < myLists.length; i++) {
                if (myList[i].name == name) {
                    return myLists[i];
                }
            }
        }
    }
}

控制器:

app.controller('MainCtrl', function( myService,$scope) {
    var testName = "test"
    myService.getMyList(testName).then(function(resp) {
        // do something with resp data
    });
});

5 个答案:

答案 0 :(得分:2)

首先需要修复拼写错误,并选择更好的命名。然后你需要返回一个元素的承诺而不是一个元素(顺便说一句,这是控制器所期望的):

app.factory('myService', function($http) {
    // this defines a promise which, when resolved, contains an array of elements
    var listPromise = $http.get("http://myService/json.data").then(function(resp) {
        return resp.data;
    });

    return {
        // this returns a promise which, when resolved, contains the element with the given name
        getElementFromList: function(name) {
            return listPromise.then(function(list) {
                return list.filter(function(element) {
                    return element.name === name;
                })[0];
            });
        }
    };
});

答案 1 :(得分:0)

每个HTTP调用都会以角度返回promise,因此在您的服务中只返回HTTP调用并返回promise

然后在您的控制器中,您可以使用thenerror回拨来处理来自serviceapi来电的回复。

<强>工厂:

app.factory('myService', function($http) {
    var myList = [];
    return {
        getMyList: function (name) {
            $http.get("http://myService/json.data")
        }
    }
}

<强>控制器:

app.controller('MainCtrl', function( myService,$scope) {
    var testName = "test"
    myService.getMyList()
    .then(function successCallback(resp) // Success call back
     {
          if(resp.data)
          {
            myLists = resp.data;
            for (var i = 0; i < myLists.length; i++) {
                if (myList[i].name == testName) { // you can use your testName here itself.
                    return myLists[i];
                }
            }

          }
    },
     function errorCallback(resp)  // Error call back
     {
      console.log(resp)
     });
});

答案 2 :(得分:0)

如果您正在使用某些客户端路由器实现:请查看Route.ResolveUi.Router实现的angular .module('test', []) .constant('API', 'https://jsonplaceholder.typicode.com') .factory("PostResolved", function($http, API) { var result = []; $http .get(API + '/posts/1') .then(function(response) { result.push(response.data); }) ; return result; }) .controller('TestCtrl', function($scope, PostResolved) { $scope.posts = PostResolved; }) ;

如果你没有任何路由器,那么,你可以做一个小技巧......只需从你的工厂返回一个对象引用,并在解决时,用预期的方法填充该对象值:

&#13;
&#13;
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.2.23/angular.min.js"></script>

<section ng-app="test">
<article ng-controller="TestCtrl">
  <div ng-repeat="post in posts">
    <h1 ng-bind="post.title"></h1>
  </div>
</article>
</section>
&#13;
Quantity
&#13;
&#13;
&#13;

答案 3 :(得分:0)

为什么不使用以下内容:

&#13;
&#13;
app.factory('myService', function($http) {
    return {
        getMyList: function (name) {
            var myList = [];
            $http.get("http://myService/json.data").then(function (resp) {
                myLists = resp.data;
            });
          
            scope.$evalAsync(function () {
                for (var i = 0; i < myLists.length; i++) {
                    if (myList[i].name == name) {
                        return myLists[i];
                    }
                }
            });
        }
    }
}
&#13;
&#13;
&#13;

答案 4 :(得分:0)

我设法通过使用$ timeout来解决这个问题。任何有更好建议的人都会告诉我。我无法获得范围。$ evalAsync工作

服务

app.factory('myService', function($http, $timeout) {
    var lists = [];

    $http.get("http://myService/json.data").then(function (resp) {
        lists = resp.data;
    });

    return {
        getMyList: function (name) {
            return $timeout(function() {
                for (var i = 0; i < lists.length; i++) {
                    if (lists[i].name == name) {
                        return lists[i];
                    }
                }
        }, 2000)

    }
}

控制器

app.controller('MainCtrl', function( myService,$scope) {
    var testName = "test"
    myService.getMyList(testName).then(function(resp) {
        // do something with resp data
    });
});