Get Even More Visitors To Your Blog, Upgrade To A Business Listing >>

How to do for loop in javascript without blocking

How to do for loop in javascript without blocking

Problem

I have folowing script

var email_list = ['[email protected]', '[email protected]',....'[email protected]'];
for(i=0;i

This code will be Blocking in nodejs how to make this non blocking?

Problem courtesy of: Yalamber

Solution

You can do this without blocking the event Loop at all, by using a recursive loop. This way what you end up with is only launching one database worker per call, at a give time. Assuming the database work you were doing was asynchronous, your code didn't really block the event loop. But the foor loop still launched a bunch of workers simultaneously, which will tend to clog the event loop(not block it). And you are right in that it is blocking the event loop while your for loop is counting from 0, to whatever the size of your array is. The following does exactly the same thing, but you only launch one database worker at a time(good), and you never count from 0 to length. Each worker is popped off the list after the work on the current email is done, and your global event loop is left to process other things, not email_list.length database requests simultaneously.

var email_list = ['[email protected]', '[email protected]', '[email protected]'];


function checkEmailList(emails, emailCallBack, completionCallback) {

    var someDataCollectdOverAllEmails = '';

    function checkEmailAsync(email) {
        db.doSomeDBWorkAsync(email, function (data) {

            someDataCollectdOverAllEmails += data;

            if (email_list.length) {
                checkEmail(email_list.pop()); //If there are still emails to be checked, check the next one ine line
            } else {
                completionCallback(someDataCollectdOverAllEmails);//IF not, call the completionCallBack
            }

            emailCallBack(data);
        });
    }

    checkEmailAsync(emails.pop());
}

function logIndividualEmailData(data) {
    console.log('Sningle Email: ' + data);
}

function logGlobalEmailData(data) {
    console.log('All Email Data: ' + data);
}

checkEmailList(email_list, logIndividualEmailData, logGlobalEmailData);

Process.nextTick example

process.nextTick(function () {
    'use strict';
    console.log('printed second');
    while (true); 
});

process.nextTick(function () {
    'use strict';
    console.log('never printed');
});

console.log('printed first');

Note however that in the example below, despite the fact that loopForever will run forever, it still allows both of our files to be read out. If we just had while(true) it would of course block and not allow this and one of our files data would not be printed out.

var files = ['blah.js', 'file.js'];
for(var i = 0; i 
Solution courtesy of: ChrisCM

Discussion

View additional discussion.



This post first appeared on Node.js Recipes, please read the originial post: here

Share the post

How to do for loop in javascript without blocking

×

Subscribe to Node.js Recipes

Get updates delivered right to your inbox!

Thank you for your subscription

×