Skip to content

Instantly share code, notes, and snippets.

@benjie
Created December 4, 2016 05:12
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 benjie/2b98bbbb14bcb07207c468316b3ee097 to your computer and use it in GitHub Desktop.
Save benjie/2b98bbbb14bcb07207c468316b3ee097 to your computer and use it in GitHub Desktop.
A monoclejs-like purely promise based asynchronous generator iterator thingy (where you can relatively safely sprinkle `yield` everywhere)
function isIterator(obj) {
return (obj && typeof obj === 'object' && typeof obj.next === 'function' && typeof obj.throw === 'function');
}
function isPromise(obj) {
return (obj && typeof obj === 'object' && typeof obj.then === 'function');
}
function o_P() {
var _resolve, _reject;
var promise = new Promise(function (resolve, reject) {
_resolve = resolve;
_reject = reject;
});
promise._resolve = _resolve;
promise._reject = _reject;
return promise;
}
function o_R(iterator, promise, toGenErr, toGenVal) {
var iteratorResult;
if (!promise) {
promise = o_P();
}
for (;;) {
try {
if (toGenErr) {
iteratorResult = iterator.throw(toGenErr);
} else {
iteratorResult = iterator.next(toGenVal);
}
} catch (e) {
promise._reject(e);
return promise;
}
var value = iteratorResult.value;
if (iteratorResult.done) {
promise._resolve(value);
return promise;
}
var nextPromise;
if (isPromise(value)) {
nextPromise = value;
} else if (isIterator(value)) {
nextPromise = o_R(value);
} else {
toGenErr = undefined;
toGenVal = value;
}
if (nextPromise) {
nextPromise.then(
function(nextValue) {return o_R(iterator, promise, undefined, nextValue)},
function(err) {o_R(iterator, promise, err, undefined);}
);
return promise;
}
}
return promise;
}
function o_O(generator) {
var fn = function() {
var result;
try {
result = generator.apply(this, Array.prototype.slice.call(arguments));
} catch (e) {
return Promise.reject(e);
}
if (isIterator(result)) {
return o_R(result);
}
return Promise.resolve(result);
}
return fn;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment