加入收藏 | 设为首页 | 会员中心 | 我要投稿 李大同 (https://www.lidatong.com.cn/)- 科技、建站、经验、云计算、5G、大数据,站长网!
当前位置: 首页 > 综合聚焦 > 服务器 > 安全 > 正文

angularjs – 服务是否会暴露其异步?

发布时间:2020-12-17 08:11:22 所属栏目:安全 来源:网络整理
导读:我正在写一个将异步检索数据的服务($ http或$ resource)。我可以通过返回最初为空的数组来隐藏它是异步的,但最终将被填充: .factory('NewsfeedService1',['$http',function($http) { var posts = []; var server_queried = false; return { posts: functio
我正在写一个将异步检索数据的服务($ http或$ resource)。我可以通过返回最初为空的数组来隐藏它是异步的,但最终将被填充:
.factory('NewsfeedService1',['$http',function($http) {
   var posts = [];
   var server_queried = false;
   return {
      posts: function() {
         if(!server_queried) {
            $http.get('json1.txt').success(
              function(data) {
                server_queried = true;
                angular.copy(data,posts);
            });
         }
         return posts;
      }
   };
}])
.controller('Ctrl1',['$scope','NewsfeedService1',function($scope,NewsfeedService1) {
    $scope.posts = NewsfeedService1.posts();
}])

或者我可以通过返回承诺来揭示异步:

.factory('NewsfeedService2',function($http) {
  var posts = [];
  var server_queried = false;
  var promise;
  return {
     posts_async: function() {
       if(!promise || !server_queried) {
         promise = $http.get('json2.txt').then(
           function(response) {
              server_queried = true;
              posts = response.data;
              return posts;
         });
       }
       return promise;
     }
  };
}])

.controller('Ctrl2','NewsfeedService2',NewsfeedService2) {
  NewsfeedService2.posts_async().then(
    function(posts) {
      $scope.posts = posts;
  });
  // or take advantage of the fact that $q promises are
  // recognized by Angular's templating engine:
  // (note that Peter and Pawel's AngularJS book recommends against this,p. 100)
  $scope.posts2 = NewsfeedService2.posts_async();
}]);

(Plunker – 如果有人想要玩上述两个实现)

暴露非同步性的一个潜在优点是,我可以通过向then()方法添加一个错误处理程序来处理控制器中的错误。但是,我可能会在应用程序范围的interceptor中捕捉和处理$ http错误。

那么,服务的异步何时被暴露出来?

我的猜测是,你会发现这个围墙两旁的人。就个人而言,我觉得你应该总是暴露一个库或函数的异步(或者更正确地说:我觉得你永远不应该隐藏一个库或函数的异步)。主要原因是透明度;例如,这个工作吗?
app.controller('MyController',function(NewsfeedService) {
  $scope.posts = NewsfeedService.posts();
  doSomethingWithPosts($scope.posts); // <-- will this work?
});

如果您使用第一种方法(例如$资源),即使$ scope.posts在技术上是一个数组,也不会。如果doSomethingWithPosts有自己的异步操作,那么你可能会遇到一个竞争条件。相反,您必须使用异步代码:

app.controller('MyController',function(NewsfeedService) {
  $scope.posts = NewsfeedService.posts(function() {
    doSomethingWithPosts($scope.posts);
  });
});

(当然,你可以使回调接受帖子作为参数,但我仍然认为这是混乱和非标准的。)

幸运的是,我们有承诺,承诺的目的是代表一个行动的未来价值。此外,由于使用Angular的$ q库创建的承诺可以绑定到视图,没有任何错误:

app.controller('MyController',function(NewsfeedService) {
  $scope.posts = NewsfeedService.posts();
  // $scope.posts is a promise,but when it resolves
  // the AngularJS view will work as intended.
});

[更新:你不能再直接约束承诺给视图;您必须等待解决承诺并手动分配范围属性。]

除此之外,Restangular是一种流行的$资源替代品,它使用承诺,AngularJS自己的$资源将在1.2中支持它们(他们可能已经在最新的1.1.x版本中支持它们)。

(编辑:李大同)

【声明】本站内容均来自网络,其相关言论仅代表作者个人观点,不代表本站立场。若无意侵犯到您的权利,请及时与联系站长删除相关内容!

    推荐文章
      热点阅读