public function __construct(Promise $promise)
{
$promise->watch(function ($data) {
foreach ($this->watchers as list($func, $cbData)) {
$func($data, $cbData);
}
});
parent::__construct($promise);
// DO NOT MOVE - preserve order in which things happen
$when = function ($e, $bool) use(&$continue) {
$continue = $bool;
};
$promise->when(function () use(&$continue, $when) {
$this->valid()->when($when);
while ($continue) {
$string[] = $this->consume();
$this->valid()->when($when);
}
$this->valid()->when(function ($ex) use(&$e) {
$e = $ex;
});
if (isset($string)) {
if (isset($string[1])) {
$string = implode($string);
} else {
$string = $string[0];
}
// way to restart, so that even after the success, the valid() / consume() API will still work
if (!$e) {
$result = $this->consume();
// consume the final result
}
$deferred = new \Amp\Deferred();
parent::__construct($deferred->promise());
$deferred->update($string);
if ($e) {
$deferred->fail($e);
} else {
$deferred->succeed($result);
}
} else {
$string = "";
}
$this->string = $string;
$this->error = $e;
foreach ($this->whens as list($when, $data)) {
$when($e, $string, $data);
}
$this->whens = $this->watchers = [];
});
}