| 18677 | */ |
| 18678 | Q.defer = defer; |
| 18679 | function defer() { |
| 18680 | // if "messages" is an "Array", that indicates that the promise has not yet |
| 18681 | // been resolved. If it is "undefined", it has been resolved. Each |
| 18682 | // element of the messages array is itself an array of complete arguments to |
| 18683 | // forward to the resolved promise. We coerce the resolution value to a |
| 18684 | // promise using the `resolve` function because it handles both fully |
| 18685 | // non-thenable values and other thenables gracefully. |
| 18686 | var messages = [], progressListeners = [], resolvedPromise; |
| 18687 | |
| 18688 | var deferred = object_create(defer.prototype); |
| 18689 | var promise = object_create(Promise.prototype); |
| 18690 | |
| 18691 | promise.promiseDispatch = function (resolve, op, operands) { |
| 18692 | var args = array_slice(arguments); |
| 18693 | if (messages) { |
| 18694 | messages.push(args); |
| 18695 | if (op === "when" && operands[1]) { // progress operand |
| 18696 | progressListeners.push(operands[1]); |
| 18697 | } |
| 18698 | } else { |
| 18699 | Q.nextTick(function () { |
| 18700 | resolvedPromise.promiseDispatch.apply(resolvedPromise, args); |
| 18701 | }); |
| 18702 | } |
| 18703 | }; |
| 18704 | |
| 18705 | // XXX deprecated |
| 18706 | promise.valueOf = function () { |
| 18707 | if (messages) { |
| 18708 | return promise; |
| 18709 | } |
| 18710 | var nearerValue = nearer(resolvedPromise); |
| 18711 | if (isPromise(nearerValue)) { |
| 18712 | resolvedPromise = nearerValue; // shorten chain |
| 18713 | } |
| 18714 | return nearerValue; |
| 18715 | }; |
| 18716 | |
| 18717 | promise.inspect = function () { |
| 18718 | if (!resolvedPromise) { |
| 18719 | return { state: "pending" }; |
| 18720 | } |
| 18721 | return resolvedPromise.inspect(); |
| 18722 | }; |
| 18723 | |
| 18724 | if (Q.longStackSupport && hasStacks) { |
| 18725 | try { |
| 18726 | throw new Error(); |
| 18727 | } catch (e) { |
| 18728 | // NOTE: don't try to use `Error.captureStackTrace` or transfer the |
| 18729 | // accessor around; that causes memory leaks as per GH-111. Just |
| 18730 | // reify the stack trace as a string ASAP. |
| 18731 | // |
| 18732 | // At the same time, cut off the first line; it's always just |
| 18733 | // "[object Promise]\n", as per the `toString`. |
| 18734 | promise.stack = e.stack.substring(e.stack.indexOf("\n") + 1); |
| 18735 | } |
| 18736 | } |