Your problem has nothing to do with call blocking; this is due to the fact that you can open a certain number of connections simultaneously to one host. After you click the maximum number of open connections, other asynchronous calls to http.get will have to wait until the number of open connections decreases again, which will happen when the remaining requests are completed and their callbacks are started. Since you create new queries faster than they flow, you get your seemingly blocking results.
Here is a modified version of your program that I created to test this. (Note that there is an easier way to solve your problem, as mtomis points out - more on this below.) I added some console.log logs, so itโs easier to say what things were being processed; I also reject all requests for anything other than / , so favicon.ico requests are ignored. Finally, I make requests to many different websites.
var http = require('http'); // http://mostpopularwebsites.net/1-50/ var sites = [ "www.google.com", "www.facebook.com", "www.youtube.com", "www.yahoo.com", "www.blogspot.com", "www.baidu.com", "www.live.com", "www.wikipedia.org", "www.twitter.com", "www.qq.com", "www.msn.com", "www.yahoo.co.jp", "www.sina.com.cn", "www.google.co.in", "www.taobao.com", "www.amazon.com", "www.linkedin.com", "www.google.com.hk", "www.wordpress.com", "www.google.de", "www.bing.com", "www.google.co.uk", "www.yandex.ru", "www.ebay.com", "www.google.co.jp", "www.microsoft.com", "www.google.fr", "www.163.com", "www.google.com.br", "www.googleusercontent.com", "www.flickr.com" ]; var server = http.createServer(function(req, res) { console.log("Got a connection."); if(req.url != "/") { console.log("But returning because the path was not '/'"); res.end(); return; } var counter = 0; for(var i = 1; i <= 30; i++) { http.get({ host: sites[i] }, function(index, host, r) { counter++; console.log("Response " + counter + " from # " + index + " (" + host + ")"); res.write("Response " + counter + " from # " + index + " (" + host + ")\n"); if(counter == 30) res.end(); }.bind(this, i, sites[i])); } console.log("Done with for loop."); }); server.listen(8000);
I ran this program and visited the page very quickly in two different browsers (I also dropped my DNS cache, because the test worked too fast to get a good output otherwise). Here is the result:
Got a connection. Done with for loop. Response 1 from
As you can see, apart from the time period when I needed to press Alt+Tab Enter , the callbacks are completely confused - asynchronous, non-blocking I / O at its best.
[change]
As stated in mtomis, the number of maximum connections that you can open for each host is configured using the global http.globalAgent.maxSockets . Just set this number of concurrent connections that you want to handle for each host, and the problem you are observing disappears.