Skip to content

Instantly share code, notes, and snippets.

@benjamn
Last active August 29, 2015 14:22
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save benjamn/b23dcb4cc6472be12291 to your computer and use it in GitHub Desktop.
Save benjamn/b23dcb4cc6472be12291 to your computer and use it in GitHub Desktop.
AwaitArgument example
let runtime = {
awrap(argument) {
return new AwaitArgument(argument);
},
"async"(generatorFunction) {
let generator = generatorFunction();
let previousPromise;
function callNext(...args) {
let result = generator.next(...args);
if (result.value instanceof AwaitArgument) {
// If the generator yields an AwaitArgument, return a Promise for
// the eventual result of the next yield (or return).
return Promise.resolve(result.value.argument).then(
result => generator.next(result),
error => generator.throw(error)
);
}
// If the generator produced an iteration result with an unwrapped
// .value, simply return that iteration result.
return result;
}
return { // Simplified AsyncIterator object (no .throw or .return).
next(...args) {
let currentPromise = previousPromise
? previousPromise.then(() => callNext(...args))
: new Promise(resolve => resolve(callNext(...args)));
previousPromise = currentPromise.catch(() => "suppressed");
return currentPromise;
}
};
}
};
// This wrapper type can remain an implementation detail, visible only to
// methods of the runtime.
class AwaitArgument {
constructor(arg) {
this.argument = arg;
}
}
export default runtime;
import runtime from "./asyncRuntime.es6.js";
function getLinesAsync(fileName) {
return runtime.async(function*() {
let asyncFile = openFileAsync(fileName);
let lineCount = 0;
while (true) {
// In an async generator function, expressions of the form `await x`
// become `yield runtime.awrap(x)`, thus yielding an AwaitArgument.
let line = yield runtime.awrap(asyncFile.getLine());
if (line === null) {
break;
}
++lineCount;
// Normal yield expressions don't need to be transformed.
let action = yield runtime.awrap(yield line);
if (action === "break") {
break;
}
}
return lineCount;
});
}
async function *getLinesAsync(fileName) {
let asyncFile = openFileAsync(fileName);
let lineCount = 0;
while (true) {
// Assume asyncFile.getLine() returns a Promise<String | null>.
let line = await asyncFile.getLine();
if (line === null) {
break;
}
++lineCount;
// In case this line requires asynchronous processing, await the
// result of the yield expression.
let action = await yield line;
if (action === "break") {
break;
}
}
return lineCount;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment