处理ajax请求的流控制(即只在前一个请求完成后处理下一个请求)
Flow control of processing ajax requests (i.e. only processing the next request after the previous request has completed)
我写了下面的代码,但我有一个问题,在分配$scope.sessionKey = data.result;
之前,它被传递到下一个ajax调用result.params.sSessionKey = $scope.sessionKey
(是的,result.name=='get_session_key'
评估循环的第一次迭代)。正如你所看到的,我已经尝试过使用$q
,但是所有关于承诺和延迟的教程对我来说都没有任何意义(甚至像这样的东西也没有帮助我)。
你能告诉我如何在angular.forEach(...
上循环,并且只在前一个测试完成时执行下一个测试吗?
// Angular's implementation of JSON-RPC (as seen here > http://jsfiddle.net/89D4b/1/)
angular.module("JSON-RPC",[]).config([...]);
// Angular
var app = angular.module('testsApp', ['JSON-RPC']);
app.controller('testsCtrl', function($scope, $http, $q) {
// populates the table on startup
$http.get("functions_as_JSON.php")
.success(function(response) {
// store the data locally for angular to loop through
$scope.data = response;
// create a promise for the sessionKey
var defer = $q.defer();
var promise = defer.promise;
promise.then(function(data){
$scope.sessionKey = data.result;
});
////////// AUTO RUN THE TESTS //////////
angular.forEach($scope.data.results,function(value,index){
$scope.runTest(value);
});
});
// test function
$scope.runTest = function(result) {
// (on all but the first test ...)
// if the sessionKey is in the JSON put it in the params to send with the JSON-RPC
if(result.params.sSessionKey) { result.params.sSessionKey = $scope.sessionKey; }
// test the method
$http.jsonrpc($scope.data.endPoint, result.method, result.params)
.success(function(data, status, headers, config) {
// if there are no errors
if (data.error === null && !data.result.status) {
// on the first test the sessionKey gets stored
if(result.name=='get_session_key') {
$scope.sessionKey = data.result;
//defer.resolve(data);
//$scope.$evalAsync(function($scope) { $scope.sessionKey = data.result; });
}
$scope.testSuccess(result, data, status, headers, config);
} else {
$scope.testFailed(result, data, status, headers, config);
}
})
.error(function(data, status, headers, config){ $scope.testFailed(result, data, status, headers, config); });
}
$scope.testSuccess = function(result, data, status, headers, config) {
result.response = {'status':status, 'post':result.params, 'data':JSON.stringify(data)};
result.status_class = 'positive';
result.status = 'success';
}
$scope.testFailed = function(result, data, status, headers, config) {
result.response = {'status':status, 'post':result.params, 'data':JSON.stringify(data)};
result.status_class = 'negative';
result.status = 'failed';
}
});
编辑
我已将其修改为以下内容,但仍无济于事
// Angular's implementation of JSON-RPC (as seen here > http://jsfiddle.net/89D4b/1/)
angular.module("JSON-RPC",[]).config([...]);
// Angular
var app = angular.module('testsApp', ['JSON-RPC']);
app.controller('testsCtrl', function($scope, $http, $q, $timeout) {
// populates the table on startup
$http.get("limesurvey_api_functions_as_JSON.php")
.success(function(response) {
// store the data locally for angular to loop through
$scope.data = response;
////////// AUTO RUN THE TESTS //////////
var promiseArray = [];
angular.forEach($scope.data.results,function(value,index){
promiseArray.push($scope.runTest(value));
});
$q.all(promiseArray).then(function(){
console.log("Angular is fun !!");
});
});
// test function
$scope.runTest = function(result){
return { then: function(Resolve,Reject){
// if the sessionKey has been set put it in the params
if(result.params.sSessionKey) { result.params.sSessionKey = $scope.sessionKey; console.log($scope.sessionKey); }
// test the method
$http.jsonrpc($scope.data.endPoint, result.method, result.params)
.success(function(data, status, headers, config) {
// if there are no errors
if (data.error === null && !data.result.status) {
// if it's the first test store the sessionKey
if(result.method=='get_session_key') {
$scope.sessionKey = data.result;
if ($scope.sessionKey == data.result) { Resolve(); }
} else {
Resolve();
}
$scope.testSuccess(result, data, status, headers, config);
} else {
Reject();
$scope.testFailed(result, data, status, headers, config);
}
})
.error(function(data, status, headers, config){
Reject();
$scope.testFailed(result, data, status, headers, config);
});
}}
}
$scope.testSuccess = function(result, data, status, headers, config) {
...
}
$scope.testFailed = function(result, data, status, headers, config) {
...
}
});
编辑2
这个
////////// AUTO RUN THE TESTS //////////
angular.forEach($scope.data.results,function(value,index){
$scope.runTest(value).then(function(data) {
if(result.method=='get_session_key') {
// if it's the first test store the sessionKey
$scope.sessionKey = data.result;
}
});
});
...
// test function
$scope.runTest = function(result){
var deferred = $q.defer();
// if the sessionKey has been set put it in the params
if(result.params.sSessionKey) { result.params.sSessionKey = $scope.sessionKey; console.log($scope.sessionKey); }
// test the method
$http.jsonrpc($scope.data.endPoint, result.method, result.params)
.success(function(data, status, headers, config) {
// if there are no errors
if (data.error === null && !data.result.status) {
$scope.testSuccess(result, data, status, headers, config);
deferred.resolve(data);
} else {
$scope.testFailed(result, data, status, headers, config);
deferred.reject(data);
}
})
.error(function(data, status, headers, config){
$scope.testFailed(result, data, status, headers, config);
deferred.reject(data);
});
return deferred.promise;
}
这并不像你想象的那么难。
根据您的评论编辑:
$http.get("functions_as_JSON.php")
.success(function(response) {
$scope.data = response;
$scope.sessionKey = data.result;
var promiseArray = [];
angular.forEach($scope.data.results,function(value,index){
promiseArray.push($scope.runTestPromise(value));
});
$q.all(promises).then(function(){
alert("Angular is fun !!");
});
});
$scope.runTestPromise = function(data){
return { then: function(Resolve,Reject){
if (data == "valid data"){
Resolve("valid data");
} else {
Reject("invalid data");
}
}
我没有运行代码,但这是练习,你把你的测试包在一个承诺,然后你让$q一个接一个地解决它们。
好了,我终于让它运行起来了:
// populates the table on startup
$http.get("functions_as_JSON.php")
.success(function(response) {
// store the data locally for angular to loop through
$scope.data = response;
////////// AUTO RUN THE TESTS //////////
var currentFunctionIndex = 0;
function nextTest() {
if (currentFunctionIndex < $scope.data.results.length) {
$scope.runTest($scope.data.results[currentFunctionIndex++]).then(nextTest);
}
}
nextTest();
});
...
// test function
$scope.runTest = function(result){
var deferred = $q.defer();
// if the sessionKey has been set put it in the params
if(result.params.sSessionKey) { result.params.sSessionKey = $scope.sessionKey; }
// test the method
$http.jsonrpc($scope.data.endPoint, result.method, result.params)
.success(function(data, status, headers, config) {
// if there are no errors
if (data.error === null && !data.result.status) {
// if it's the first test store the sessionKey
if(result.method=='get_session_key') {
$scope.sessionKey = data.result;
}
$scope.testSuccess(result, data, status, headers, config);
deferred.resolve();
} else {
$scope.testFailed(result, data, status, headers, config);
deferred.reject();
}
})
.error(function(data, status, headers, config){
$scope.testFailed(result, data, status, headers, config);
deferred.reject();
});
return deferred.promise;
}
我有点理解为什么会这样,但在我看来,在文档中可以做更多的事情来解释这一点(特别是当循环通过数据时)
相关文章:
- 正在传递JSONP标头's数据参数到另一个文件中的AJAX请求
- 请求一个完整的响应对象,而不是紧凑的响应对象foursquare场地搜索api
- 我应该请求一个大块数据还是一系列较小的 ajax 请求
- 我可以请求一个带有JavaScript的网页,然后将其按原样发送到服务器进行进一步分析吗?
- 我使用XMLHttpRequest作为菜单,当我请求一个包含javascript的页面HTML时,没有任何反应,为什么
- 当请求一个JS文件时,为什么需要cookie信息(会话ID)
- 在Node.js中,使用Prompt请求一个值,并在主js文件中使用该值
- dojo/使用NodeJS请求一个png图像数组缓冲区,并将图像返回给客户端
- 在php中请求一个select选项
- 如何从角度工厂用循环发送过程请求(一个接一个)
- 我如何使用AJAX从web服务器请求一个变量
- Ajax:批量url列表在文本区发送请求一个接一个,并显示重复的答案
- 在javascript原型中请求一个方法
- jQuery 2 ajax请求一个是onClick
- AngularJS:当使用$http请求一个文件(json content)时发生SyntaxError
- CORS标头未设置-我可以请求一个图像url,然后将其发送回自己吗
- 从html向node.js请求一个变量
- 向java请求一个json参数,以将json数组转换为java数组
- 混合内容页:请求一个不安全的样式表错误
- HMLHttpRequest无法加载.我试图POST请求一个JSON对象到firebase