call(back)
FrontendmediumSign in to star problems

Drive a Generator Like async/await

Before async/await was syntax, generators plus a small runner did the same job. Implement run(genFn).

run starts the generator and returns a promise. Each time the generator yields a value, run waits for it (plain values count as already resolved) and resumes the generator with the result. A rejection is thrown into the generator at the yield, where a try/catch can handle it. run resolves with the generator's return value and rejects if the generator throws.

run(function* () {
  const user = yield fetchUser(1);        // resumes with the user
  try { yield fetchPosts(user.id); }       // a rejection lands here
  catch (err) { return "no posts: " + err.message; }
});

The grader runs your code on a virtual clock, with generators that yield timed promises.

Hints

Hint 1

Write a step(method, arg) that calls it[method](arg) inside a try. A throw there means the generator didn't catch it: reject.

Hint 2

Resolve when the result is done. Otherwise wrap the value in Promise.resolve and continue with step("next", value) or step("throw", err).

Asked at