在循环中有多个AJAX请求的情况下如何将XMLHTTP请求链接到正确的响应 [英] How to link XMLHTTP Request to right Response in case of multiple AJAX request in a loop

查看:56
本文介绍了在循环中有多个AJAX请求的情况下如何将XMLHTTP请求链接到正确的响应的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在尝试在for循环内发送多个AJAX请求.我需要确保响应已链接到正在做出的正确请求.我正在遵循此处发布的解决方案 XMLHttpRequest for for循环在这里,fileBatches是循环的大小.我正在尝试捕获响应,该响应表示关于成功和失败的请求数量的信息,并尝试将其存储在_finalResponseArray中.如果fileBatches的长度为3,则第一个请求可能比其他请求花费更多的时间.考虑第一个请求,需要花费一些时间来处理,到那时,第二个请求和第三个请求将完成,然后第一个请求将完成.我需要确保正确的请求已链接到正确的响应.在这里,当第一个循环开始(i = 0)时,需要花费一些时间来处理,而到第二个循环开始时(i = 1)才需要处理.XHR [i] .readyState == 4(因为我增加了1,并且如何获得i = 0的值?)感到困惑,并且我无法获得链接到正确请求的响应.请在下面找到代码.下面的函数将针对多个AJAX请求执行.

I am trying to send multiple AJAX request inside a for loop. I need to make sure that responses are getting linked to the right request that are being made. I am following the solution that is posted here XMLHttpRequest in for loop Here, fileBatches is the size of the loop. I am trying to capture the response which says the information about the number of requests succeeded and failed and trying to store it in _finalResponseArray. If the length of the fileBatches is 3, there are chances that first request may take more time than other request. Consider first request, takes sometime to process and by the time, second request and third request would have completed and then first request would complete. I need to make sure that right request is getting linked to right response. Here when the first loop starts(i=0), it takes sometime to get processed and by the time second loop starts (i=1) and gets processed. XHR[i].readyState == 4 (since i has incremented 1 and how to get the value of i = 0?) gets confused and I am not able to get the response linked to the right request. Please find the code below. Below function gets executed for multiple AJAX request.

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);
}

我不确定我在这里做错了什么,但是请求没有链接到正确的响应,它们被随机添加到_finalResponseArray中.如果只有一个请求而没有任何循环,则它可以完美地工作.如何确保验证了onreadystatechange是否为正确的循环?

I am not sure what I am making wrong here, but the requests are not getting linked to correct responses and they randomly gets added to _finalResponseArray. It works perfectly if there is only one request without any loop. How to make sure that onreadystatechange is verified for correct loop?

**********更新

**********Updates

尝试了注释中建议的解决方案以及各种其他方法(请参考堆栈溢出中的过去问题):

Tried solution as suggested in comments and also various other approaches (referring past questions in stack overflow):

即使我尝试使用闭包,响应也弄乱了.对于所有3个请求,它随机选择一个响应,并为所有3个请求产生相同的响应.

Even though I try to use closures, response messes up. For all 3 requests, it randomly picks a response and produces same response for all 3 requests.

我的请求应该具有唯一性,以便响应可以正确跟踪它.当我们尝试发送ant GET或POST请求时,我确实看到迭代器值'i'被附加到URL,但是我只是针对不同的请求发送相同的URL.那有关系吗

Should my request have something unique so that response can track it correctly. I do see the iterator value 'i' was appended to URL when we try to send ant GET or POST request, but I am just sending same URL for different requests. Does that matter?

推荐答案

首先,我建议使用所谓的 XMLHttpRequest 2.0 -而不是简单的onreadystatechange之类的东西,只需使用 onload onloadend (您会在下面的代码中看到为什么要使用后者)

Firstly, I'd recommend using so called XMLHttpRequest 2.0 - rather than the fiddly onreadystatechange stuff, just use onload and onloadend (you'll see why the latter in the code below)

由于 XMLHttpRequest 的异步特性,您无法预测请求何时完成,因此 _finalResponseArray 仅在最终的 onloadend 完成

Due to the asynchronous nature of XMLHttpRequest you can't predict when the requests are all done, so _finalResponseArray will only be complete once the final onloadend is complete

添加一定数量的完整请求后,所有请求完成后,您就可以在 onloadend 回调中执行所需的任何操作.无论成功或失败,都会调用onloadend

Adding a count of complete requests will allow you to do whatever you need in the onloadend callback once all requests have finished. onloadend is called regardless of success or failure

我也使用 .forEach 代替IIFE

I also use .forEach instead of IIFE

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

这篇关于在循环中有多个AJAX请求的情况下如何将XMLHTTP请求链接到正确的响应的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆