Modern Asynchronous JavaScript: using variable name inside its iterator? (page 7)

Within the body of the asynchronous iterator, the code uses srcArr to refer to the array it’s being called on; since it’s a named function and not an arrow func, why not usethis instead? Seems like that would be less brittle and more general.

Hi Mark,

Thanks for reading my book! Because we have a nested function in the iterator, this would refer to next() rather than srcArr. If you replace srcArr with this at line 11 and 16 you’ll get an error.

One workaround is to write const self = this; at the top level of the iterator and replace srcArr with self, like this:

const srcArr = [
  'https://eloux.com/async_js/examples/1.json',
  'https://eloux.com/async_js/examples/2.json',
  'https://eloux.com/async_js/examples/3.json',
];

srcArr[Symbol.asyncIterator] = function() { //<label id="code.asyncIterator"/>
  let i = 0;
  const self = this;
  return {
    async next() {
      if (i === self.length) { //<label id="code.length"/>
        return {
          done: true
        };
      }
      const url = self[i++];
      const response = await fetch(url);
      if (!response.ok) {  //<label id="code.ok"/>
        throw new Error('Unable to retrieve URL: ' + url);
      }
      return {
        value: await response.json(),
        done: false
      };
    }
  };
};

const iterator = srcArr[Symbol.asyncIterator]();

iterator.next().then(result => {
  console.log(result.value.firstName);  // ⇒ John
});

iterator.next().then(result => {
  console.log(result.value.firstName);  // ⇒ Peter
});

iterator.next().then(result => {
  console.log(result.value.firstName);  // ⇒ Anna
});

Let me know if you have any other question :blush: