调用$http()(或任何别名,例如$http.get() 等)会立即调用网络请求(除非检查员或第三方组件进行任何操作)。它类似于在其他框架(如 jQuery)中发出 XmlHttpRequest 或 JSONP 请求。
服务被创建为单例,因此它们在第一次被请求时创建一次,并且从那时起注入相同的实例。该服务的作用完全取决于您,因为 Angular 只处理实例化它、解析它的任何依赖项并将其注入到任何需要它的地方。
如果您的应用程序需要长时间运行并需要使用数据进行更新,则您需要对其进行适当的架构设计。显然,我不知道您的规范的全部要求或细节,但我可以给您一些提示,也许可以帮助您。
高级,听起来你需要一个函数来操作一个定时器(使用$timeout服务),如果你达到或超过一个时间窗口,调用一个$http请求来检索最新的数据和路由它以及需要它的各种组件。然后,它应该标记下一次操作的时间范围,然后再次设置超时,以便它可以在更远的地方醒来,看看是否是时候再次工作了。
首先要考虑的是这个功能应该放在哪里?如果您只需要它发生在某个控制器中,那么您可以使用$timeout 和$http 在该控制器中完成所有操作。另一方面,如果您需要在多个地方重用这些数据,您将需要使用服务。如果您很可能使用某项服务,那么您需要找出将这些更改应用到需要它的各个部分的最佳方法。
我的建议是当您的 $http 请求更新数据时,在您的服务中使用 $rootScope 到 $broadcast 上的 Angular 事件。然后,使用此数据的各种控制器、服务和指令可以使用 $scope.$on 订阅此事件并做出适当的反应。这使服务与使用它的事物分离,并允许它们轻松地对更改做出反应。
服务所做的只是设置一个超时,当它失效时检查数据,如果它有数据,在$rootScope上的一个事件中广播数据,并设置另一个超时。客户端在接收到来自服务的事件时,只会监听并使用新数据更新其本地范围。
This plunk 包含一个愚蠢的例子。您可能希望将其更改为在一天中的某个时间或您认为合适的任何时间安排工作,然后让它发出$http 请求,而不是发送当前日期。
angular.module("demo", [])
.service('myService', ['$rootScope', '$timeout', '$http', function($rootScope, $timeout, $http) {
var state = { timeout: null, next: null };
function work() {
var now = Date.now();
if (now >= state.next) { // you can replace with your own logic to schedule when it should occur (like a specific time of day). in this example, we poll every second, but do work every 5.
// this is where your $http service can do work, something like $http.get(...).success(function(data) { $rootScope.$broadcast('myService.data', data); });
$rootScope.$broadcast('myService.data', new Date());
state.next = now + 5000; // do work every five seconds
}
state.timeout = $timeout(work, 1000); // poll every second
}
return {
start: function() {
if (state.timeout) $timeout.cancel(state.timeout); // cancel pending timeout
work(); // first time will just schedule work to be done in the future
},
stop: function() {
if (state.timeout) $timeout.cancel(state.timeout); // cancel pending timeout
}
};
}])
.controller('DemoCtrl', ['$scope', function($scope) {
$scope.title = "Hello, World";
// here, the controller subscribes to the event, and when it occurs, it copies the event data to a local scope item
$scope.$on('myService.data', function(evt, data) {
$scope.$apply(function() {
$scope.myServiceData = data;
});
});
}])
.run(['myService', function(myService) {
myService.start(); // starts the service when the app runs
}]);