【发布时间】:2015-08-03 06:05:36
【问题描述】:
在我的 Angular 应用程序中,我有两个控制器都需要访问相同的数据。
为此,我创建了一个服务,负责保存和提供对该数据的访问:
angular.module("SomeModule").factory( "SomeService", function( $http ) {
var svc = {};
var data = {};
// on initialization, load data from the server
$http.get( "somefile.json" )
.success( function( data ) {
svc.data = data;
} );
svc.getItem = function( id ) {
// find the specified item within svc.data, and return its value
};
return svc;
} );
...我已经将该服务注入到两个控制器中的每一个中:
angular.module("SomeModule").controller( "SomeController", function( $routeParams, SomeService ) {
var ctrl = this;
ctrl.item = null; // set an initial value
// load the item that was requested in the URL
ctrl.item = SomeService.getItem( $routeParams.id );
} );
这几乎有效 - 但它有一个很大的缺陷。如果SomeController 在SomeService 完成加载somefile.json 之前调用SomeService.getItem(),那么SomeService 将没有任何数据要返回。
实际上,如果我多次加载应用程序,一些加载会起作用(ie,SomeService将首先完成加载somefile.json,然后控制器将根据需要显示数据),而其他加载则不会(ie,SomeController 将在数据实际加载之前尝试从 SomeService 检索数据,一切都会崩溃并烧毁)。
显然,我需要找到一些方法来推迟getItem() 的执行,直到SomeService 实际上准备好处理这些调用。但我不确定最好的方法。
我能想到一些相当麻烦的解决方案,比如在SomeService 中建立我自己的呼叫队列,并连接一堆复杂的回调。但是必须有一个更优雅的解决方案。
我怀疑Angular's $q service 在这里可能有用。但是,我对 Promise 很陌生,我不确定我应该如何在这里使用 $q(甚至我是否在正确地吠叫)。
你能把我推向正确的方向吗?我会非常感激的。
【问题讨论】:
-
只需让
getItem返回一个承诺 - 并将数据的承诺存储在svc.data中,而不是“准备就绪的数据”。 -
正如@Bergi 所说,您必须返回一个承诺。你在我的回答中有一些例子,如果你想了解这方面的详细信息,请检查第二个重点
-
正如@Bergi 建议的那样,我在我的答案中调整了这个例子以适应你的情况。
标签: angularjs asynchronous promise angularjs-service angular-promise