Javascript 在AngularJS服务中使用承诺
我正在将一些代码从Silverlight迁移到AngularJS。我的Silverlight代码基本上会尝试访问web服务。如果失败,它将稍等片刻,然后重试。它会尝试这三次。我现在试着用AngularJS做这个 根据我的理解,我应该使用AngularJS服务来访问我的web服务。据我理解,承诺是被使用的。目前,我有以下服务:Javascript 在AngularJS服务中使用承诺,javascript,angularjs,Javascript,Angularjs,我正在将一些代码从Silverlight迁移到AngularJS。我的Silverlight代码基本上会尝试访问web服务。如果失败,它将稍等片刻,然后重试。它会尝试这三次。我现在试着用AngularJS做这个 根据我的理解,我应该使用AngularJS服务来访问我的web服务。据我理解,承诺是被使用的。目前,我有以下服务: 'use strict'; myApp.service('$myService', function($rootScope, $http) { this.queryAt
'use strict';
myApp.service('$myService', function($rootScope, $http) {
this.queryAttempt = 0;
this.findRecent = function() {
this.queryAttempt = 0;
};
this.attemptToGetRecent = function() {
try {
this.queryAttempt = this.queryAttempt + 1;
if (this.recentQueryAttempt < 3) {
$http.get('http://www.someserver.com/endpoint');
} else {
console.log('signal failure');
}
} catch (ex1) {
console.log('Error Finding Recent (2).');
}
};
});
“严格使用”;
myApp.service(“$myService”,函数($rootScope,$http){
this.queryattent=0;
this.findRecent=函数(){
this.queryattent=0;
};
this.attemptToGetRecent=函数(){
试一试{
this.queryattest=this.queryattest+1;
如果(此.recentquery尝试<3){
$http.get('http://www.someserver.com/endpoint');
}否则{
控制台日志(“信号故障”);
}
}捕获(ex1){
log('查找最近的错误(2)。');
}
};
});
由于承诺被使用,我有点迷茫。在Silverlight中,我创建了事件。我的控制器将调用$myService.findRecent()。我想检测成功和失败。但是,我还需要一些重试逻辑。如果我不需要重试逻辑,我只需要在findRecent函数中使用return$http.get(…)。但是,由于重试逻辑的需要,我不知道如何构造我的承诺,以便控制器知道a)成功,b)如果尝试了三次,但失败了,那么控制器会知道失败
有人能告诉我如何在承诺的世界里解决这个问题吗?让我在下面的评论中发布代码:
myApp.service('myService', function($rootScope, $http, $q) {
var findRecent - function() {
var deferred = $q.defer();
attemptToGetRecent(0, deferred);
return deferred.promise;
};
var attemptToGetRecent = function(count, deferred) {
$http.get('http://www.someserver.com/endpoint')
.success(function (response) {
deferred.resolve(response);
})
.error(function() {
if (count >= 3) {
deferred.reject();
} else {
attemptToGetRecent(count++, deffered);
}
});
};
});
$q
服务实例中,创建延迟对象
(承诺)你自己attemptoGetRecent
函数,该函数将
不断递归地调用自己,直到努力的次数过多为止
高attemptotoGetRecent
将尝试调用服务器,如果
成功它解决了你的承诺与数据。如果呼叫失败,
它将被再次调用最多3个计时器,然后拒绝您的承诺myService.findRecent()
.then(function (data) {
console.log(data);
$scope.videos = data.feed.entry;
}, function() {
console.log("error");
});
};
为了便于阅读,我删除了控制台日志记录。当然可以加上。另外,最好不要用前导$命名您自己的服务,这是为angular服务保留的
工作示例:
您可以注入$q并使用它来做出自己的承诺,并创建一个递归函数来处理这些尝试 以下是一些应该有帮助的代码:
'use strict';
myApp.service('$myService', function ($rootScope, $http, $q) {
this.getRecent = function(){
var deferred = $q.defer();
var attempts = 0;
(function queryRecent(attempts, error){
if(attempts >= 2){
// the $http.get() failed 3 times
deferred.reject(error);
}else{
$http.get('http://www.someserver.com/endpoint').then(function(response){
// success -> resolve any data you want
deferred.resolve({
attempts: attempts,
response: response
});
}).catch(function(error){
// failed, retry the queryRecent recursive function
queryRecent(attempts + 1, error); // pass attempts + 1 and the error object
});
}
})(attempts, ''); // initially pass 0 and '' to the queryRecent recursive function
return deferred.promise;
};
});
myApp.controller('MyCtrl', function($scope, $myService){
$myService.getRecent().then(function(data){
// success -> use data
console.log(data);
}).catch(function(error){
// the $http.get() failed 3 times
console.log(error);
});
});
当我执行这段代码时,我得到一个未处理的异常。这与消费者代码有关。服务代码似乎工作得很好。但是,在使用者中不会调用.success |错误代码。我只是在控制台窗口中看到“undefined不是一个函数”。我在findRecent函数中输入了deferred。代码的其余部分似乎还可以。请调试它,并检查到底什么是未定义的,或者如果你可以提供小提琴。谢谢在发布评论之前,我已经修复了延迟的错误。不幸的是,我似乎无法让调试器告诉我什么是未定义的。我现在在打电话,如果有帮助的话,我明天可以为你创建工作小提琴。代码中有一些拼写错误。我编辑了我的答案并添加了工作示例。链接是: