|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
"use strict"; |
|
module.exports = function(Promise, INTERNAL) { |
|
var errors = require("./errors.js"); |
|
var TypeError = errors.TypeError; |
|
var util = require("./util.js"); |
|
var isArray = util.isArray; |
|
var errorObj = util.errorObj; |
|
var tryCatch1 = util.tryCatch1; |
|
|
|
function PromiseSpawn(generatorFunction, receiver, caller) { |
|
var promise = this._promise = new Promise(INTERNAL); |
|
promise._setTrace(caller, void 0); |
|
this._generatorFunction = generatorFunction; |
|
this._receiver = receiver; |
|
this._generator = void 0; |
|
} |
|
|
|
PromiseSpawn.prototype.promise = function PromiseSpawn$promise() { |
|
return this._promise; |
|
}; |
|
|
|
PromiseSpawn.prototype._run = function PromiseSpawn$_run() { |
|
this._generator = this._generatorFunction.call(this._receiver); |
|
this._receiver = |
|
this._generatorFunction = void 0; |
|
this._next(void 0); |
|
}; |
|
|
|
PromiseSpawn.prototype._continue = function PromiseSpawn$_continue(result) { |
|
if (result === errorObj) { |
|
this._generator = void 0; |
|
var trace = errors.canAttach(result.e) |
|
? result.e : new Error(result.e + ""); |
|
this._promise._attachExtraTrace(trace); |
|
this._promise._reject(result.e, trace); |
|
return; |
|
} |
|
|
|
var value = result.value; |
|
if (result.done === true) { |
|
this._generator = void 0; |
|
if (!this._promise._tryFollow(value)) { |
|
this._promise._fulfill(value); |
|
} |
|
} |
|
else { |
|
var maybePromise = Promise._cast(value, PromiseSpawn$_continue, void 0); |
|
if (!(maybePromise instanceof Promise)) { |
|
if (isArray(maybePromise)) { |
|
maybePromise = Promise.all(maybePromise); |
|
} |
|
else { |
|
this._throw(new TypeError( |
|
"A value was yielded that could not be treated as a promise" |
|
)); |
|
return; |
|
} |
|
} |
|
maybePromise._then( |
|
this._next, |
|
this._throw, |
|
void 0, |
|
this, |
|
null, |
|
void 0 |
|
); |
|
} |
|
}; |
|
|
|
PromiseSpawn.prototype._throw = function PromiseSpawn$_throw(reason) { |
|
if (errors.canAttach(reason)) |
|
this._promise._attachExtraTrace(reason); |
|
this._continue( |
|
tryCatch1(this._generator["throw"], this._generator, reason) |
|
); |
|
}; |
|
|
|
PromiseSpawn.prototype._next = function PromiseSpawn$_next(value) { |
|
this._continue( |
|
tryCatch1(this._generator.next, this._generator, value) |
|
); |
|
}; |
|
|
|
return PromiseSpawn; |
|
}; |
|
|