Ad

How To Make Learnyounode #9 Juggling Async Work

I am trying to go through nodeschool's learnyounode.

This problem is the same as the previous problem (HTTP COLLECT) in that you need to use http.get(). However, this time you will be provided with three URLs as the first three command-line arguments.

You must collect the complete content provided to you by each of the URLs and print it to the console (stdout). You don't need to print out the length, just the data as a String; one line per URL. The catch is that you must print them out in the same order as the URLs are provided to you as command-line arguments.

Here is my code:

var bl = require('bl');
var http = require('http');

var urls = [process.argv[2], process.argv[3], process.argv[4]]
var dataArray = [];
var count = 0;


for (var i = 0; i <= urls.length-1; i++) {
  http.get(urls[i], function(response){ 
    response.setEncoding('utf8').pipe(bl(function (err, data) { 
      dataArray[i] = data.toString();
      count++;
      if (count==2){
        dataArray.forEach(function(item){
          console.log(item);
        })
      }
    }));
  });

};

And when I try to verify it:

  1. ACTUAL: "She'll be right gyno mate flat out like a milk bar. Grab us a gutta also mad as a battler. "
  2. EXPECTED: "Lets get some parma to watch out for the pav. She'll be right slabs no worries he's got a massive cracker. Lets get some gobful flamin she'll be right thongs. "

  3. ACTUAL: ""

  4. EXPECTED: "Get a dog up ya ute with it'll be sickie. He's got a massive yobbo bloody as cross as a bonza. "

  5. ACTUAL:

  6. EXPECTED: "She'll be right gyno mate flat out like a milk bar. Grab us a gutta also mad as a battler. "

  7. ACTUAL:

  8. EXPECTED: ""

What am I doing wrong here?

Ad

Answer

You want to check if count == 3 because you have 3 urls.

Also you don't want to use a function within a loop like that. In this case the value of i is 3 every time your anonymous function is executed ... That's why you're only outputting the expected value of the third url.

This is a great example of whats going on: JavaScript closure inside loops – simple practical example

By wrapping the function in a new function you can make sure that i is exactly what you want it to be.

This should work:

var bl = require('bl');
var http = require('http');

var urls = [process.argv[2], process.argv[3], process.argv[4]];
var dataArray = [];
var count = 0;


function juggle (i) {
  http.get(urls[i], function(response) {
    response.setEncoding('utf8').pipe(bl(function(err, data) {
      dataArray[i] = data.toString();
      count++;
      if (count == 3) {
        dataArray.forEach(function(item) {
          console.log(item);
        });
      }
    }));
  });
}

for (var i = 0; i < 3; i++) {
  juggle(i)
}
Ad
source: stackoverflow.com
Ad