public function reject($reason) { //parent promise is rejected - we just reject (there is not ON_REJECTED) if (is_null($this->data[Store::ON_REJECTED])) { return parent::reject($reason); } //parent promise is rejected by promise - we has new parent promise if ($reason instanceof PromiseInterface) { $promiseIdOfResult = $reason->getId(); $this->data[Store::PARENT_ID] = $promiseIdOfResult; $this->data[Store::ON_FULFILLED] = $this->data[Store::ON_REJECTED]; return $this->getData(); } //parent promise is rejected by value - we try run ON_REJECTED callback $onRejectedCallback = unserialize($this->data[Store::ON_REJECTED]); try { $result = call_user_func($onRejectedCallback, $reason); // if $onRejectedCallback can not resolve problem it must throw exception } catch (\Exception $ex) { return parent::reject($ex); } // if $onRejectedCallback has resolved problem it return result return parent::resolve($result); }