Skip to content

Commit 51c1173

Browse files
committed
fix: Make rejection handlers reusable;
remove `exit(255)` from RejectionPromise;
1 parent 5389858 commit 51c1173

File tree

3 files changed

+16
-22
lines changed

3 files changed

+16
-22
lines changed

composer.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,7 @@
6464
"sort-packages": true
6565
},
6666
"scripts": {
67-
"stan": "stan",
67+
"stan": "phpstan",
6868
"test": "phpunit --color=always --testdox",
6969
"test:cc": [
7070
"@putenv XDEBUG_MODE=coverage",

src/Internal/RejectedPromise.php

Lines changed: 10 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -14,44 +14,35 @@
1414
*/
1515
final class RejectedPromise implements PromiseInterface
1616
{
17-
/** @var \Throwable */
18-
private $reason;
17+
private \Throwable $reason;
18+
private bool $handled = false;
19+
private static ?\Closure $rejectionHandler = null;
1920

20-
/** @var bool */
21-
private $handled = false;
22-
23-
/**
24-
* @param \Throwable $reason
25-
*/
2621
public function __construct(\Throwable $reason)
2722
{
2823
$this->reason = $reason;
2924
}
3025

26+
public static function setRejectionHandler(?callable $handler): void
27+
{
28+
self::$rejectionHandler = $handler === null ? null : $handler(...);
29+
}
30+
3131
/** @throws void */
3232
public function __destruct()
3333
{
34-
if ($this->handled) {
35-
return;
36-
}
37-
38-
$handler = set_rejection_handler(null);
39-
if ($handler === null) {
40-
$message = 'Unhandled promise rejection with ' . $this->reason;
41-
42-
\error_log($message);
34+
if ($this->handled || self::$rejectionHandler === null) {
4335
return;
4436
}
4537

4638
try {
47-
$handler($this->reason);
39+
(self::$rejectionHandler)($this->reason);
4840
} catch (\Throwable $e) {
4941
\preg_match('/^([^:\s]++)(.*+)$/sm', (string) $e, $match);
5042
\assert(isset($match[1], $match[2]));
5143
$message = 'Fatal error: Uncaught ' . $match[1] . ' from unhandled promise rejection handler' . $match[2];
5244

5345
\error_log($message);
54-
exit(255);
5546
}
5647
}
5748

src/functions.php

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -249,18 +249,21 @@ function (\Throwable $reason) use ($i, &$reasons, &$toReject, $reject, &$continu
249249
* [`finally()` method](#promiseinterfacefinally).
250250
* See also the [`reject()` function](#reject) for more details.
251251
*
252-
* @param callable(\Throwable):void|null $callback
253-
* @return callable(\Throwable):void|null
252+
* @param callable(\Throwable):mixed|null $callback
253+
* @return callable(\Throwable):mixed|null
254254
*/
255255
function set_rejection_handler(?callable $callback): ?callable
256256
{
257257
static $current = null;
258258
$previous = $current;
259259
$current = $callback;
260+
RejectedPromise::setRejectionHandler($current);
260261

261262
return $previous;
262263
}
263264

265+
set_rejection_handler(static fn(\Throwable $reason) => \error_log('Unhandled promise rejection with ' . $reason));
266+
264267
/**
265268
* @internal
266269
*/

0 commit comments

Comments
 (0)