Incorporating a delay into looped HTTP requests while effectively utilizing Promise.all to track their completion

Greetings! In my current project, I am trying to introduce a 50ms delay before each subsequent HTTP request is sent to the server. Additionally, I aim to incorporate a functionality that triggers after all requests have been successfully made.

To better explain my intentions, here's an example illustrating what I'm aiming for:

Below you'll find an example of an Express API that I've put together:

app.get('/morans/test', (req, res) => {
    console.log(`start test request`);
    let targetUrl = `http://-domain-/solr/genea_expression/smplGeoclust?q=text:"GO:0003674"&stats.facet=geohash_3&rows=10320`;
    let i = 0;
    let promises = [];

    console.log(`making request ${i}`);


    for (let i = 0; i < 200; i++) {
        setTimeout(
            () => {
                let testReq = new Promise((resolve, reject) => {
                    http.get(targetUrl, (result) => {
                        result.on('data', (chunk) => {
                            console.log(`working ${i}`);
                        }).on('end', () => {
                            console.log(`ending ${i}`);
                        }).on('error', (err) => {
                            console.log(`this is error message ${err}`);
                        })
                    })
                });

                promises.push(testReq);
            }, 50 * i
        )
    }
    Promise.all(promises).then(() => {
        console.log(`done`);
    });
});

Although the delay functions correctly, there seems to be an issue with the Promise.all(promises)... statement as it triggers prematurely (console.log('done') appears once the first request is sent). Without any timeout, everything runs smoothly. My suspicion is that the setTimeout function doesn't provide enough time for the promise to be added to the promises array. How can I adjust the code so that each HTTP request is spaced 50ms apart and still know when all requests have been completed successfully?

Answer №1

When Promise.all is called, the promises array is empty because none of the timeouts have expired yet.

To ensure that Promise.all is called only when all promises are pushed into the array, move the call inside the timeout callback after pushing the promise and checking the array length:

for (let i = 0; i < 200; i++) {
    setTimeout(
        () => {
            // ...etc ... etc
            promises.push(testReq);
            if (promises.length == 200) { // <---- include this condition
                Promise.all(promises).then(() => {
                    console.log(`done`);
                });
            } 
        }, 50 * i
    )
}

Don't forget to call resolve() in your new Promise callback to avoid pending promises:

                    .on('end', () => {
                        console.log(`ending ${i}`);
                        resolve();
                    })

Refer to the documentation on http.get for details on getting response data. Ensure to pass this data as an argument to resolve.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

The value of "asp-route-id" is dynamically determined through the use of

Hey there, I’m looking to dynamically pass a value from "codeDrink" to my controller using "asp-route-id" and Ajax in my ASP.NET MVC project. This is how I am handling it in my view: <p> <a id="deleteLink" asp-action="Delete& ...

Establish a global variable within the utils.js module in a Node.js environment

Hey there, I'm currently in the process of trying to figure out how to properly define a global variable in node.js. I am aware that it's not considered best practice, but in this specific scenario, it seems like the only way to go without involv ...

Running Javascript based on the output of PHP code

I have been working on my code with test.php that should trigger some Javascript when my PHP code, conditional.php, detects input and submits it. However, instead of executing the expected "Do Something in Javascript," it outputs "Not empty" instead. I fin ...

Exploring Data within Data Structures

I am currently making two JSON requests in my code: d3.json("path/to/file1.json", function(error, json) { d3.json("path/to/file2.json", function(error, json2) { }); }); The structure of json 2 looks like this: [ { "city" : "LA", "locati ...

Unlock a multitude of outcomes with Sequelize

Is there a way to retrieve multiple results from Sequelize and store them in an array? For example, I want to fetch all the values in the name field from the test table and display them in the console. This is what I tried: test.findAll().them(function(re ...

`Is there a way to avoid extra re-renders caused by parameters in NextJS?`

I am currently in the process of implementing a standard loading strategy for NextJS applications using framer-motion. function MyApp({ Component, pageProps, router }) { const [isFirstMount, setIsFirstMount] = useState(true); useEffect(() => { ...

Discovering the worth of specific selections in a dropdown menu

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script> </head> <body> <select name="states" id="states"> <option value="100">Hawaii</option> <option value="107">Texa ...

React Hooks: Unable to re-enable input after it has been disabled

Attempting to manage the status of my points input whether it's enabled or disabled, I encountered an issue. Upon checking the checkbox, it correctly gets disabled. However, upon unchecking it, the input remains disabled. Initially, I attempted settin ...

`Express.js Controllers: The Key to Context Binding`

I'm currently working on a project in Express.js that involves a UserController class with methods like getAllUsers and findUserById. When using these methods in my User router, I have to bind each method when creating an instance of the UserControlle ...

Creating a personalized to-do list feature in NodeJs for exclusive user access: A step-by-step guide

After pondering over this issue for the past few days, I am still trying to grasp it. My web app allows users to login and create a list of students. My goal is to ensure that only the user who created the list can view it. Below is my progress so far. Co ...

The onClick() function in JavaScript is encountering issues on the Firefox OS mobile application

I've been working on an app for Firefox OS mobile devices where I'm trying to trigger a Javascript function onClick() from a div attribute. It's functioning properly in regular browsers, but when I test it in the simulator, the onClick funct ...

How to filter jQuery DataTables by column using comparison operators

Recently, I've been utilizing the amazing DataTables jQuery plugin along with the filter plug in. But now, I find myself pondering if there's a way to filter table columns by row using a comparison operator (such as '<', '>', ...

Encountering a Typescript issue with mongoose

Working with node.js and various email addresses, I encountered a compile error: TS2345: Argument of type '(error: any, document: any) => void' is not assignable to parameter of type '(err: any) => void'. This error occurs at the l ...

Disappearance of array data

I have been working on creating an array of objects with nested arrays, but I am facing an issue where data seems to go missing in the final step: const args_arr = []; const options_arr = []; let options = ''; let text = ""; for (let i = 0; ...

Unable to dynamically change the value of the submit button using angular.js

I'm facing an issue with setting the submit button value dynamically using Angular.js. The code I've written below explains my problem. <body ng-controller="MainCtrl"> <input type="submit" value="{{ !model ? 'reset' : mod ...

The contents of req.body resemble an empty {}

Does anyone know why the req.body is empty in this code snippet? Even though all form data is submitted, it doesn't seem to be recognized in the req.body. Strangely enough, it works perfectly fine in postman. Take a look at the server-side code: con ...

GET method returns an empty array in the express node server

app.get('/:user/:tag', function (req, res) { fs.readdir( 'api'+path.sep+req.params.user, function (err, files) { var tweets=[]; for (var i =1, j=files.length ; i <j; i++) { fs.readFile('api'+path.sep+ ...

Understanding the getJSON MethodExplaining how

$.getJSON( main_url + "tasks/", { "task":8, "last":lastMsgID } I'm a bit confused about how this code functions. I'm looking for a way to retrieve messages from a shoutbox using a URL or some sort of method that the function here ...

One of the essential components in Angular is currently absent

After integrating Angular4 with Visual Studio 2017 following the steps outlined in this article, I realized that my setup also involved using Nodejs 8.6.0 and npm 5.4.2 - which were the latest versions at the time. Despite having vs2017 generate a fold ...

Validating a string using regular expressions in JavaScript

Input needed: A string that specifies the range of ZIP codes the user intends to use. Examples: If the user wants to use all zip codes from 1000 to 1200: They should enter 1000:1200 If they want to use only ZIP codes 1000 and 1200: They should enter ...