PluginProbe ʕ •ᴥ•ʔ
SEOPress – AI SEO Plugin & On-site SEO / 9.3.0.3
SEOPress – AI SEO Plugin & On-site SEO v9.3.0.3
10.0.1 10.0 9.9.2 9.9.1 9.9 9.8.5 9.8.4 9.8.3 9.8.2 9.8.1 trunk 7.0 7.0.1 7.0.2 7.0.3 7.1 7.1.1 7.1.2 7.2 7.3 7.3.1 7.3.2 7.4 7.5 7.5.0.1 7.5.0.2 7.5.0.3 7.5.1 7.5.2 7.5.2.1 7.6 7.6.1 7.7 7.7.1 7.7.2 7.8 7.9 7.9.1 7.9.2 8.0 8.0.1 8.1 8.1.1 8.2 8.3 8.3.1 8.4 8.4.1 8.5 8.5.0.2 8.5.1 8.5.1.1 8.6 8.6.1 8.7 8.7.0.1 8.7.0.2 8.8 8.8.1 8.9 8.9.0.1 8.9.0.2 9.0 9.0.1 9.1 9.2 9.3 9.3.0.1 9.3.0.2 9.3.0.3 9.3.0.4 9.4 9.4.1 9.5 9.6 9.7 9.7.1 9.7.2 9.7.3 9.7.4 9.8
wp-seopress / vendor / guzzlehttp / promises / README.md
wp-seopress / vendor / guzzlehttp / promises Last commit date
src 7 months ago CHANGELOG.md 7 months ago LICENSE 7 months ago README.md 7 months ago composer.json 7 months ago
README.md
560 lines
1 # Guzzle Promises
2
3 [](https://promisesaplus.com/Promises/A+](https://promisesaplus.com/](https://promisesaplus.com/) implementation that handles promise
4 chaining and resolution iteratively, allowing for "infinite" promise chaining
5 while keeping the stack size constant. Read [](https://blog.domenic.me/youre-missing-the-point-of-promises/this blog post](https://blog.domenic.me/youre-missing-the-point-of-promises/](https://blog.domenic.me/youre-missing-the-point-of-promises/)
6 for a general introduction to promises.
7
8 - [](#featuresFeatures](#features](#features)
9 - [](#quick-startQuick start](#quick-start](#quick-start)
10 - [](#synchronous-waitSynchronous wait](#synchronous-wait](#synchronous-wait)
11 - [](#cancellationCancellation](#cancellation](#cancellation)
12 - [](#apiAPI](#api](#api)
13 - [](#promisePromise](#promise](#promise)
14 - [](#fulfilledpromiseFulfilledPromise](#fulfilledpromise](#fulfilledpromise)
15 - [](#rejectedpromiseRejectedPromise](#rejectedpromise](#rejectedpromise)
16 - [](#promise-interopPromise interop](#promise-interop](#promise-interop)
17 - [](#implementation-notesImplementation notes](#implementation-notes](#implementation-notes)
18
19
20 ## Features
21
22 - [](https://promisesaplus.com/Promises/A+](https://promisesaplus.com/](https://promisesaplus.com/) implementation.
23 - Promise resolution and chaining is handled iteratively, allowing for
24 "infinite" promise chaining.
25 - Promises have a synchronous `wait` method.
26 - Promises can be cancelled.
27 - Works with any object that has a `then` function.
28 - C# style async/await coroutine promises using
29 `GuzzleHttp\Promise\Coroutine::of()`.
30
31
32 ## Installation
33
34 ```shell
35 composer require guzzlehttp/promises
36 ```
37
38
39 ## Version Guidance
40
41 | Version | Status | PHP Version |
42 |---------|---------------------|--------------|
43 | 1.x | Security fixes only | >=5.5,<8.3 |
44 | 2.x | Latest | >=7.2.5,<8.6 |
45
46
47 ## Quick Start
48
49 A *promise* represents the eventual result of an asynchronous operation. The
50 primary way of interacting with a promise is through its `then` method, which
51 registers callbacks to receive either a promise's eventual value or the reason
52 why the promise cannot be fulfilled.
53
54 ### Callbacks
55
56 Callbacks are registered with the `then` method by providing an optional
57 `$onFulfilled` followed by an optional `$onRejected` function.
58
59
60 ```php
61 use GuzzleHttp\Promise\Promise;
62
63 $promise = new Promise();
64 $promise->then(
65 // $onFulfilled
66 function ($value) {
67 echo 'The promise was fulfilled.';
68 },
69 // $onRejected
70 function ($reason) {
71 echo 'The promise was rejected.';
72 }
73 );
74 ```
75
76 *Resolving* a promise means that you either fulfill a promise with a *value* or
77 reject a promise with a *reason*. Resolving a promise triggers callbacks
78 registered with the promise's `then` method. These callbacks are triggered
79 only once and in the order in which they were added.
80
81 ### Resolving a Promise
82
83 Promises are fulfilled using the `resolve($value)` method. Resolving a promise
84 with any value other than a `GuzzleHttp\Promise\RejectedPromise` will trigger
85 all of the onFulfilled callbacks (resolving a promise with a rejected promise
86 will reject the promise and trigger the `$onRejected` callbacks).
87
88 ```php
89 use GuzzleHttp\Promise\Promise;
90
91 $promise = new Promise();
92 $promise
93 ->then(function ($value) {
94 // Return a value and don't break the chain
95 return "Hello, " . $value;
96 })
97 // This then is executed after the first then and receives the value
98 // returned from the first then.
99 ->then(function ($value) {
100 echo $value;
101 });
102
103 // Resolving the promise triggers the $onFulfilled callbacks and outputs
104 // "Hello, reader."
105 $promise->resolve('reader.');
106 ```
107
108 ### Promise Forwarding
109
110 Promises can be chained one after the other. Each then in the chain is a new
111 promise. The return value of a promise is what's forwarded to the next
112 promise in the chain. Returning a promise in a `then` callback will cause the
113 subsequent promises in the chain to only be fulfilled when the returned promise
114 has been fulfilled. The next promise in the chain will be invoked with the
115 resolved value of the promise.
116
117 ```php
118 use GuzzleHttp\Promise\Promise;
119
120 $promise = new Promise();
121 $nextPromise = new Promise();
122
123 $promise
124 ->then(function ($value) use ($nextPromise) {
125 echo $value;
126 return $nextPromise;
127 })
128 ->then(function ($value) {
129 echo $value;
130 });
131
132 // Triggers the first callback and outputs "A"
133 $promise->resolve('A');
134 // Triggers the second callback and outputs "B"
135 $nextPromise->resolve('B');
136 ```
137
138 ### Promise Rejection
139
140 When a promise is rejected, the `$onRejected` callbacks are invoked with the
141 rejection reason.
142
143 ```php
144 use GuzzleHttp\Promise\Promise;
145
146 $promise = new Promise();
147 $promise->then(null, function ($reason) {
148 echo $reason;
149 });
150
151 $promise->reject('Error!');
152 // Outputs "Error!"
153 ```
154
155 ### Rejection Forwarding
156
157 If an exception is thrown in an `$onRejected` callback, subsequent
158 `$onRejected` callbacks are invoked with the thrown exception as the reason.
159
160 ```php
161 use GuzzleHttp\Promise\Promise;
162
163 $promise = new Promise();
164 $promise->then(null, function ($reason) {
165 throw new Exception($reason);
166 })->then(null, function ($reason) {
167 assert($reason->getMessage() === 'Error!');
168 });
169
170 $promise->reject('Error!');
171 ```
172
173 You can also forward a rejection down the promise chain by returning a
174 `GuzzleHttp\Promise\RejectedPromise` in either an `$onFulfilled` or
175 `$onRejected` callback.
176
177 ```php
178 use GuzzleHttp\Promise\Promise;
179 use GuzzleHttp\Promise\RejectedPromise;
180
181 $promise = new Promise();
182 $promise->then(null, function ($reason) {
183 return new RejectedPromise($reason);
184 })->then(null, function ($reason) {
185 assert($reason === 'Error!');
186 });
187
188 $promise->reject('Error!');
189 ```
190
191 If an exception is not thrown in a `$onRejected` callback and the callback
192 does not return a rejected promise, downstream `$onFulfilled` callbacks are
193 invoked using the value returned from the `$onRejected` callback.
194
195 ```php
196 use GuzzleHttp\Promise\Promise;
197
198 $promise = new Promise();
199 $promise
200 ->then(null, function ($reason) {
201 return "It's ok";
202 })
203 ->then(function ($value) {
204 assert($value === "It's ok");
205 });
206
207 $promise->reject('Error!');
208 ```
209
210
211 ## Synchronous Wait
212
213 You can synchronously force promises to complete using a promise's `wait`
214 method. When creating a promise, you can provide a wait function that is used
215 to synchronously force a promise to complete. When a wait function is invoked
216 it is expected to deliver a value to the promise or reject the promise. If the
217 wait function does not deliver a value, then an exception is thrown. The wait
218 function provided to a promise constructor is invoked when the `wait` function
219 of the promise is called.
220
221 ```php
222 $promise = new Promise(function () use (&$promise) {
223 $promise->resolve('foo');
224 });
225
226 // Calling wait will return the value of the promise.
227 echo $promise->wait(); // outputs "foo"
228 ```
229
230 If an exception is encountered while invoking the wait function of a promise,
231 the promise is rejected with the exception and the exception is thrown.
232
233 ```php
234 $promise = new Promise(function () use (&$promise) {
235 throw new Exception('foo');
236 });
237
238 $promise->wait(); // throws the exception.
239 ```
240
241 Calling `wait` on a promise that has been fulfilled will not trigger the wait
242 function. It will simply return the previously resolved value.
243
244 ```php
245 $promise = new Promise(function () { die('this is not called!'); });
246 $promise->resolve('foo');
247 echo $promise->wait(); // outputs "foo"
248 ```
249
250 Calling `wait` on a promise that has been rejected will throw an exception. If
251 the rejection reason is an instance of `\Exception` the reason is thrown.
252 Otherwise, a `GuzzleHttp\Promise\RejectionException` is thrown and the reason
253 can be obtained by calling the `getReason` method of the exception.
254
255 ```php
256 $promise = new Promise();
257 $promise->reject('foo');
258 $promise->wait();
259 ```
260
261 > PHP Fatal error: Uncaught exception 'GuzzleHttp\Promise\RejectionException' with message 'The promise was rejected with value: foo'
262
263 ### Unwrapping a Promise
264
265 When synchronously waiting on a promise, you are joining the state of the
266 promise into the current state of execution (i.e., return the value of the
267 promise if it was fulfilled or throw an exception if it was rejected). This is
268 called "unwrapping" the promise. Waiting on a promise will by default unwrap
269 the promise state.
270
271 You can force a promise to resolve and *not* unwrap the state of the promise
272 by passing `false` to the first argument of the `wait` function:
273
274 ```php
275 $promise = new Promise();
276 $promise->reject('foo');
277 // This will not throw an exception. It simply ensures the promise has
278 // been resolved.
279 $promise->wait(false);
280 ```
281
282 When unwrapping a promise, the resolved value of the promise will be waited
283 upon until the unwrapped value is not a promise. This means that if you resolve
284 promise A with a promise B and unwrap promise A, the value returned by the
285 wait function will be the value delivered to promise B.
286
287 **Note**: when you do not unwrap the promise, no value is returned.
288
289
290 ## Cancellation
291
292 You can cancel a promise that has not yet been fulfilled using the `cancel()`
293 method of a promise. When creating a promise you can provide an optional
294 cancel function that when invoked cancels the action of computing a resolution
295 of the promise.
296
297
298 ## API
299
300 ### Promise
301
302 When creating a promise object, you can provide an optional `$waitFn` and
303 `$cancelFn`. `$waitFn` is a function that is invoked with no arguments and is
304 expected to resolve the promise. `$cancelFn` is a function with no arguments
305 that is expected to cancel the computation of a promise. It is invoked when the
306 `cancel()` method of a promise is called.
307
308 ```php
309 use GuzzleHttp\Promise\Promise;
310
311 $promise = new Promise(
312 function () use (&$promise) {
313 $promise->resolve('waited');
314 },
315 function () {
316 // do something that will cancel the promise computation (e.g., close
317 // a socket, cancel a database query, etc...)
318 }
319 );
320
321 assert('waited' === $promise->wait());
322 ```
323
324 A promise has the following methods:
325
326 - `then(callable $onFulfilled, callable $onRejected) : PromiseInterface`
327
328 Appends fulfillment and rejection handlers to the promise, and returns a new promise resolving to the return value of the called handler.
329
330 - `otherwise(callable $onRejected) : PromiseInterface`
331
332 Appends a rejection handler callback to the promise, and returns a new promise resolving to the return value of the callback if it is called, or to its original fulfillment value if the promise is instead fulfilled.
333
334 - `wait($unwrap = true) : mixed`
335
336 Synchronously waits on the promise to complete.
337
338 `$unwrap` controls whether or not the value of the promise is returned for a
339 fulfilled promise or if an exception is thrown if the promise is rejected.
340 This is set to `true` by default.
341
342 - `cancel()`
343
344 Attempts to cancel the promise if possible. The promise being cancelled and
345 the parent most ancestor that has not yet been resolved will also be
346 cancelled. Any promises waiting on the cancelled promise to resolve will also
347 be cancelled.
348
349 - `getState() : string`
350
351 Returns the state of the promise. One of `pending`, `fulfilled`, or
352 `rejected`.
353
354 - `resolve($value)`
355
356 Fulfills the promise with the given `$value`.
357
358 - `reject($reason)`
359
360 Rejects the promise with the given `$reason`.
361
362
363 ### FulfilledPromise
364
365 A fulfilled promise can be created to represent a promise that has been
366 fulfilled.
367
368 ```php
369 use GuzzleHttp\Promise\FulfilledPromise;
370
371 $promise = new FulfilledPromise('value');
372
373 // Fulfilled callbacks are immediately invoked.
374 $promise->then(function ($value) {
375 echo $value;
376 });
377 ```
378
379
380 ### RejectedPromise
381
382 A rejected promise can be created to represent a promise that has been
383 rejected.
384
385 ```php
386 use GuzzleHttp\Promise\RejectedPromise;
387
388 $promise = new RejectedPromise('Error');
389
390 // Rejected callbacks are immediately invoked.
391 $promise->then(null, function ($reason) {
392 echo $reason;
393 });
394 ```
395
396
397 ## Promise Interoperability
398
399 This library works with foreign promises that have a `then` method. This means
400 you can use Guzzle promises with [](https://github.com/reactphp/promiseReact promises](https://github.com/reactphp/promise](https://github.com/reactphp/promise)
401 for example. When a foreign promise is returned inside of a then method
402 callback, promise resolution will occur recursively.
403
404 ```php
405 // Create a React promise
406 $deferred = new React\Promise\Deferred();
407 $reactPromise = $deferred->promise();
408
409 // Create a Guzzle promise that is fulfilled with a React promise.
410 $guzzlePromise = new GuzzleHttp\Promise\Promise();
411 $guzzlePromise->then(function ($value) use ($reactPromise) {
412 // Do something something with the value...
413 // Return the React promise
414 return $reactPromise;
415 });
416 ```
417
418 Please note that wait and cancel chaining is no longer possible when forwarding
419 a foreign promise. You will need to wrap a third-party promise with a Guzzle
420 promise in order to utilize wait and cancel functions with foreign promises.
421
422
423 ### Event Loop Integration
424
425 In order to keep the stack size constant, Guzzle promises are resolved
426 asynchronously using a task queue. When waiting on promises synchronously, the
427 task queue will be automatically run to ensure that the blocking promise and
428 any forwarded promises are resolved. When using promises asynchronously in an
429 event loop, you will need to run the task queue on each tick of the loop. If
430 you do not run the task queue, then promises will not be resolved.
431
432 You can run the task queue using the `run()` method of the global task queue
433 instance.
434
435 ```php
436 // Get the global task queue
437 $queue = GuzzleHttp\Promise\Utils::queue();
438 $queue->run();
439 ```
440
441 For example, you could use Guzzle promises with React using a periodic timer:
442
443 ```php
444 $loop = React\EventLoop\Factory::create();
445 $loop->addPeriodicTimer(0, [$queue, 'run']);
446 ```
447
448
449 ## Implementation Notes
450
451 ### Promise Resolution and Chaining is Handled Iteratively
452
453 By shuffling pending handlers from one owner to another, promises are
454 resolved iteratively, allowing for "infinite" then chaining.
455
456 ```php
457 <?php
458 require 'vendor/autoload.php';
459
460 use GuzzleHttp\Promise\Promise;
461
462 $parent = new Promise();
463 $p = $parent;
464
465 for ($i = 0; $i < 1000; $i++) {
466 $p = $p->then(function ($v) {
467 // The stack size remains constant (a good thing)
468 echo xdebug_get_stack_depth() . ', ';
469 return $v + 1;
470 });
471 }
472
473 $parent->resolve(0);
474 var_dump($p->wait()); // int(1000)
475
476 ```
477
478 When a promise is fulfilled or rejected with a non-promise value, the promise
479 then takes ownership of the handlers of each child promise and delivers values
480 down the chain without using recursion.
481
482 When a promise is resolved with another promise, the original promise transfers
483 all of its pending handlers to the new promise. When the new promise is
484 eventually resolved, all of the pending handlers are delivered the forwarded
485 value.
486
487 ### A Promise is the Deferred
488
489 Some promise libraries implement promises using a deferred object to represent
490 a computation and a promise object to represent the delivery of the result of
491 the computation. This is a nice separation of computation and delivery because
492 consumers of the promise cannot modify the value that will be eventually
493 delivered.
494
495 One side effect of being able to implement promise resolution and chaining
496 iteratively is that you need to be able for one promise to reach into the state
497 of another promise to shuffle around ownership of handlers. In order to achieve
498 this without making the handlers of a promise publicly mutable, a promise is
499 also the deferred value, allowing promises of the same parent class to reach
500 into and modify the private properties of promises of the same type. While this
501 does allow consumers of the value to modify the resolution or rejection of the
502 deferred, it is a small price to pay for keeping the stack size constant.
503
504 ```php
505 $promise = new Promise();
506 $promise->then(function ($value) { echo $value; });
507 // The promise is the deferred value, so you can deliver a value to it.
508 $promise->resolve('foo');
509 // prints "foo"
510 ```
511
512
513 ## Upgrading from Function API
514
515 A static API was first introduced in 1.4.0, in order to mitigate problems with
516 functions conflicting between global and local copies of the package. The
517 function API was removed in 2.0.0. A migration table has been provided here for
518 your convenience:
519
520 | Original Function | Replacement Method |
521 |----------------|----------------|
522 | `queue` | `Utils::queue` |
523 | `task` | `Utils::task` |
524 | `promise_for` | `Create::promiseFor` |
525 | `rejection_for` | `Create::rejectionFor` |
526 | `exception_for` | `Create::exceptionFor` |
527 | `iter_for` | `Create::iterFor` |
528 | `inspect` | `Utils::inspect` |
529 | `inspect_all` | `Utils::inspectAll` |
530 | `unwrap` | `Utils::unwrap` |
531 | `all` | `Utils::all` |
532 | `some` | `Utils::some` |
533 | `any` | `Utils::any` |
534 | `settle` | `Utils::settle` |
535 | `each` | `Each::of` |
536 | `each_limit` | `Each::ofLimit` |
537 | `each_limit_all` | `Each::ofLimitAll` |
538 | `!is_fulfilled` | `Is::pending` |
539 | `is_fulfilled` | `Is::fulfilled` |
540 | `is_rejected` | `Is::rejected` |
541 | `is_settled` | `Is::settled` |
542 | `coroutine` | `Coroutine::of` |
543
544
545 ## Security
546
547 If you discover a security vulnerability within this package, please send an email to security@tidelift.com. All security vulnerabilities will be promptly addressed. Please do not disclose security-related issues publicly until a fix has been announced. Please see [Security Policy](https://github.com/guzzle/promises/security/policy) for more information.
548
549
550 ## License
551
552 Guzzle is made available under the MIT License (MIT). Please see [License File](LICENSE) for more information.
553
554
555 ## For Enterprise
556
557 Available as part of the Tidelift Subscription
558
559 The maintainers of Guzzle and thousands of other packages are working with Tidelift to deliver commercial support and maintenance for the open source dependencies you use to build your applications. Save time, reduce risk, and improve code health, while paying the maintainers of the exact dependencies you use. [Learn more.](https://tidelift.com/subscription/pkg/packagist-guzzlehttp-promises?utm_source=packagist-guzzlehttp-promises&utm_medium=referral&utm_campaign=enterprise&utm_term=repo)
560