/** * @param \Amp\Observable $observable * @param callable(mixed $value): bool $filter * * @return \Amp\Observable */ function filter(Observable $observable, callable $filter) : Observable { $postponed = new Postponed(); $pending = true; $observable->subscribe(function ($value) use(&$pending, $postponed, $filter) { if ($pending) { try { if (!$filter($value)) { return null; } return $postponed->emit($value); } catch (\Throwable $exception) { $pending = false; $postponed->fail($exception); } } return null; }); $observable->when(function ($exception, $value) use(&$pending, $postponed) { if (!$pending) { return; } $pending = false; if ($exception) { $postponed->fail($exception); return; } $postponed->resolve($value); }); return $postponed->observe(); }