1<?php
2
3namespace GuzzleHttp\Promise;
4
5final class Each
6{
7    /**
8     * Given an iterator that yields promises or values, returns a promise that
9     * is fulfilled with a null value when the iterator has been consumed or
10     * the aggregate promise has been fulfilled or rejected.
11     *
12     * $onFulfilled is a function that accepts the fulfilled value, iterator
13     * index, and the aggregate promise. The callback can invoke any necessary
14     * side effects and choose to resolve or reject the aggregate if needed.
15     *
16     * $onRejected is a function that accepts the rejection reason, iterator
17     * index, and the aggregate promise. The callback can invoke any necessary
18     * side effects and choose to resolve or reject the aggregate if needed.
19     *
20     * @param mixed    $iterable    Iterator or array to iterate over.
21     * @param callable $onFulfilled
22     * @param callable $onRejected
23     *
24     * @return PromiseInterface
25     */
26    public static function of(
27        $iterable,
28        callable $onFulfilled = null,
29        callable $onRejected = null
30    ) {
31        return (new EachPromise($iterable, [
32            'fulfilled' => $onFulfilled,
33            'rejected'  => $onRejected
34        ]))->promise();
35    }
36
37    /**
38     * Like of, but only allows a certain number of outstanding promises at any
39     * given time.
40     *
41     * $concurrency may be an integer or a function that accepts the number of
42     * pending promises and returns a numeric concurrency limit value to allow
43     * for dynamic a concurrency size.
44     *
45     * @param mixed        $iterable
46     * @param int|callable $concurrency
47     * @param callable     $onFulfilled
48     * @param callable     $onRejected
49     *
50     * @return PromiseInterface
51     */
52    public static function ofLimit(
53        $iterable,
54        $concurrency,
55        callable $onFulfilled = null,
56        callable $onRejected = null
57    ) {
58        return (new EachPromise($iterable, [
59            'fulfilled'   => $onFulfilled,
60            'rejected'    => $onRejected,
61            'concurrency' => $concurrency
62        ]))->promise();
63    }
64
65    /**
66     * Like limit, but ensures that no promise in the given $iterable argument
67     * is rejected. If any promise is rejected, then the aggregate promise is
68     * rejected with the encountered rejection.
69     *
70     * @param mixed        $iterable
71     * @param int|callable $concurrency
72     * @param callable     $onFulfilled
73     *
74     * @return PromiseInterface
75     */
76    public static function ofLimitAll(
77        $iterable,
78        $concurrency,
79        callable $onFulfilled = null
80    ) {
81        return each_limit(
82            $iterable,
83            $concurrency,
84            $onFulfilled,
85            function ($reason, $idx, PromiseInterface $aggregate) {
86                $aggregate->reject($reason);
87            }
88        );
89    }
90}
91