Javascript 如果循环中有多个AJAX请求,如何将XMLHTTP请求链接到正确的响应
我试图在for循环中发送多个AJAX请求。我需要确保响应与提出的正确请求相关联。我正在遵循发布在这里的解决方案 这里,fileBatches是循环的大小。我正试图捕获表示成功和失败请求数量的信息的响应,并试图将其存储在_finalResponseArray中。如果FileBatchs的长度为3,则第一个请求可能比其他请求花费更多的时间。考虑第一个请求,花一些时间来处理,并且在时间上,第二个请求和第三个请求将完成,然后第一个请求将完成。我需要确保正确的请求与正确的响应相关联。这里,当第一个循环开始(i=0)时,需要一些时间来处理,到第二个循环开始(i=1)并得到处理时。 XHR[i].readyState==4(因为我已经增加了1,如何获得i=0的值?)变得混乱,我无法获得链接到正确请求的响应。请在下面查找代码。下面的函数针对多个AJAX请求执行Javascript 如果循环中有多个AJAX请求,如何将XMLHTTP请求链接到正确的响应,javascript,ajax,asynchronous,xmlhttprequest,Javascript,Ajax,Asynchronous,Xmlhttprequest,我试图在for循环中发送多个AJAX请求。我需要确保响应与提出的正确请求相关联。我正在遵循发布在这里的解决方案 这里,fileBatches是循环的大小。我正试图捕获表示成功和失败请求数量的信息的响应,并试图将其存储在_finalResponseArray中。如果FileBatchs的长度为3,则第一个请求可能比其他请求花费更多的时间。考虑第一个请求,花一些时间来处理,并且在时间上,第二个请求和第三个请求将完成,然后第一个请求将完成。我需要确保正确的请求与正确的响应相关联。这里,当第一个循环开始
var XHR = [];
var fileBatches = "Calling a function which returns array of values that needs to be processed"
var _finalResponseArray = [];
for (var i = 0; i < fileBatches.length; i++)
{
(function(i)
{
finalBatch = []
finalBatch.push("Things that need to be processed by controller");
finalData = finalBatch.join('&').replace(/%20/g, '+'); // Sending the values in a format so that it will be received by controller
XHR[i] = new XMLHttpRequest();
console.log(i);
XHR[i].open('POST', theURL);
XHR[i].onreadystatechange = function (event)
{
console.log("Here");
if (XHR[i].readyState == 4)
{
console.log("This request is complete");
console.log("I value is " + i);
if (XHR[i].status == 200)
{
_finalResponseArray.push(XHR[i].responseText);
console.log("Inside" + _finalResponseArray);
}
}
}
XHR[i].setRequestHeader('accept', 'text/JSON');
XHR[i].send(finalData);
})(i);
}
var XHR=[];
var fileBatches=“调用返回需要处理的值数组的函数”
var _finalResponseArray=[];
对于(var i=0;i
我不确定我在这里做错了什么,但请求没有链接到正确的响应,它们随机添加到_finalResponseArray。如果只有一个请求而没有任何循环,那么它可以完美地工作。如何确保onreadystatechange被验证为正确的循环
**********更新
根据评论和其他各种方法(参考堆栈溢出中过去的问题)中的建议,尝试了解决方案:
即使我尝试使用闭包,响应也会出错。对于所有3个请求,它随机选择一个响应,并为所有3个请求生成相同的响应
我的请求是否应该具有唯一性,以便响应能够正确跟踪它。当我们尝试发送ant GET或POST请求时,我确实看到迭代器值“I”被附加到URL,但我只是为不同的请求发送相同的URL。那有关系吗 您可能希望将onreadystatechange函数逻辑拉入其自己的函数定义中,以便它可以在本地管理作用域。试试这个:
var XHR = [];
var _finalResponseArray = [];
var createReadyStateChangeCb = function(responseIdx)
{
return function(event)
{
console.log("Here");
if (XHR[responseIdx].readyState == 4)
{
console.log("This request is complete");
console.log("I value is " + responseIdx);
if (XHR[responseIdx].status == 200)
{
_finalResponseArray.push(XHR[responseIdx].responseText);
console.log("Inside" + _finalResponseArray);
}
}
}
}
for (var i = 0; i < fileBatches.length; i++)
{
(function(i)
{
finalBatch = []
finalBatch.push("Things that need to be processed by controller");
finalData = finalBatch.join('&').replace(/%20/g, '+'); // Sending the values in a format so that it will be received by controller
XHR[i] = new XMLHttpRequest();
console.log(i);
XHR[i].open('POST', theURL);
XHR[i].onreadystatechange = createReadyStateChangeCb(i);
}
XHR[i].setRequestHeader('accept', 'text/JSON');
XHR[i].send(finalData);
})(i);
}
var XHR=[];
var _finalResponseArray=[];
var createReadyStateCb=函数(响应ID)
{
返回函数(事件)
{
console.log(“此处”);
if(XHR[responseIdx].readyState==4)
{
console.log(“此请求已完成”);
log(“I值为”+responseIdx);
if(XHR[responseIdx].status==200)
{
_最终响应array.push(XHR[responseIdx].responseText);
console.log(“内部”+_finalResponseArray);
}
}
}
}
对于(var i=0;i
首先,我建议使用所谓的XMLHttpRequest 2.0
——而不是那些烦琐的onreadystatechange东西,只需使用onload
和onloadend
(下面的代码中可以看到后者的原因)
由于XMLHttpRequest
的异步性质,您无法预测请求何时全部完成,因此\u finalResponseArray
只有在最终的onloadend
完成后才会完成
添加完整请求的计数将允许您在所有请求完成后在onloadend
回调中执行所需的任何操作。无论成功或失败,都会调用onloadend
我还使用.forEach
而不是iLife
var fileBatches = "Calling a function which returns array of values that needs to be processed"
var _done = 0;
var _count = fileBatches.length;
var _finalResponseArray = [];
fileBatches.forEach(function(item, i) {
var finalBatch = []
var xhr = new XMLHttpRequest();
finalBatch.push("Things that need to be processed by controller");
finalData = finalBatch.join('&').replace(/%20/g, '+'); // Sending the values in a format so that it will be received by controller
xhr.open('POST', theURL);
xhr.onload = function (event) {
if (xhr.status == 200) {
_finalResponseArray[i] = (xhr.responseText);
}
};
xhr.onloadend = function (event) {
// this gets called in ALL cases, i.e. after load, error or abort
if(++_done == _count) {
// _finalResponseArray is complete here
}
};
xhr.setRequestHeader('accept', 'text/JSON');
xhr.send(finalData);
});
//_finalResponseArray will ALWAYS be empty here
您的缩进使代码无法读取可能
finalBatch
不在您发布的代码中-每个循环都会立即将其删除-您可能也不需要XHR
数组,因为为什么需要访问循环外的所有XHR?因为XMLHttpRequest
是异步的,所以不能保证它们将以什么顺序完成,所以也不能保证结果将以什么顺序推送到结果数组上-尝试使用\u finalResponseArray[i]=XHR.responseText
如果您需要正确的顺序-请注意,如果某些请求失败,finalResponseArray可能会有空插槽,而且,同样,由于XHR的异步性质,无法知道(使用当前代码)何时所有请求都被删除