Skip to content

Commit 2e50d3c

Browse files
committed
Add comprehensive type annotations and improve type safety across async interfaces
1 parent fcba92d commit 2e50d3c

File tree

4 files changed

+76
-187
lines changed

4 files changed

+76
-187
lines changed

src/Async/Handlers/AsyncExecutionHandler.php

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
use Fiber;
66
use Rcalicdan\FiberAsync\EventLoop\EventLoop;
7+
use Rcalicdan\FiberAsync\Promise\Interfaces\PromiseInterface;
78
use Rcalicdan\FiberAsync\Promise\Promise;
89
use Throwable;
910

@@ -22,13 +23,13 @@
2223
* The returned function, when called, will execute the original function
2324
* inside a Fiber and return a Promise that resolves with the result.
2425
*
25-
* @param callable $asyncFunction The function to make asynchronous
26-
* @return callable A function that returns a Promise when called
26+
* @param callable $asyncFunction The function to make asynchronous.
27+
* @return callable(...mixed): PromiseInterface<mixed> A function that returns a Promise when called.
2728
*/
2829
public function async(callable $asyncFunction): callable
2930
{
30-
return function (...$args) use ($asyncFunction) {
31-
return new Promise(function ($resolve, $reject) use ($asyncFunction, $args) {
31+
return function (...$args) use ($asyncFunction): PromiseInterface {
32+
return new Promise(function (callable $resolve, callable $reject) use ($asyncFunction, $args) {
3233
$fiber = new Fiber(function () use ($asyncFunction, $args, $resolve, $reject) {
3334
try {
3435
$result = $asyncFunction(...$args);
@@ -42,4 +43,4 @@ public function async(callable $asyncFunction): callable
4243
});
4344
};
4445
}
45-
}
46+
}

src/Async/Interfaces/AsyncOperationsInterface.php

Lines changed: 28 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
namespace Rcalicdan\FiberAsync\Async\Interfaces;
44

55
use Rcalicdan\FiberAsync\Promise\Interfaces\PromiseInterface;
6+
use Throwable;
67

78
/**
89
* Provides core asynchronous operations for fiber-based async programming.
@@ -15,23 +16,24 @@ interface AsyncOperationsInterface
1516
/**
1617
* Checks if the current execution context is within a fiber.
1718
*
18-
* @return bool True if executing within a fiber, false otherwise
19+
* @return bool True if executing within a fiber, false otherwise.
1920
*/
2021
public function inFiber(): bool;
2122

2223
/**
2324
* Creates a resolved promise with the given value.
2425
*
25-
* @param mixed $value The value to resolve the promise with
26-
* @return PromiseInterface A promise resolved with the provided value
26+
* @template T
27+
* @param T $value The value to resolve the promise with.
28+
* @return PromiseInterface<T> A promise resolved with the provided value.
2729
*/
2830
public function resolve(mixed $value): PromiseInterface;
2931

3032
/**
3133
* Creates a rejected promise with the given reason.
3234
*
33-
* @param mixed $reason The reason for rejection (typically an exception or error message)
34-
* @return PromiseInterface A promise rejected with the provided reason
35+
* @param mixed $reason The reason for rejection (typically an exception or error message).
36+
* @return PromiseInterface<mixed> A promise rejected with the provided reason.
3537
*/
3638
public function reject(mixed $reason): PromiseInterface;
3739

@@ -41,8 +43,8 @@ public function reject(mixed $reason): PromiseInterface;
4143
* The returned callable will execute the original function within a fiber
4244
* and return a promise that resolves with the function's result.
4345
*
44-
* @param callable $asyncFunction The function to wrap asynchronously
45-
* @return callable A callable that returns a PromiseInterface
46+
* @param callable $asyncFunction The function to wrap asynchronously.
47+
* @return callable(): PromiseInterface<mixed> A callable that returns a PromiseInterface.
4648
*/
4749
public function async(callable $asyncFunction): callable;
4850

@@ -52,18 +54,18 @@ public function async(callable $asyncFunction): callable;
5254
* This method should only be called within a fiber context.
5355
* It will yield control back to the event loop until the promise settles.
5456
*
55-
* @param PromiseInterface $promise The promise to await
56-
* @return mixed The resolved value of the promise
57-
*
58-
* @throws mixed The rejection reason if the promise is rejected
57+
* @template T
58+
* @param PromiseInterface<T> $promise The promise to await.
59+
* @return T The resolved value of the promise.
60+
* @throws Throwable The rejection reason if the promise is rejected.
5961
*/
6062
public function await(PromiseInterface $promise): mixed;
6163

6264
/**
63-
* Creates a promise that resolves after the specified delay.
65+
* Creates a promise that resolves with null after the specified delay.
6466
*
65-
* @param float $seconds The delay in seconds (supports fractions for milliseconds)
66-
* @return PromiseInterface A promise that resolves after the delay
67+
* @param float $seconds The delay in seconds (supports fractions for milliseconds).
68+
* @return PromiseInterface<null> A promise that resolves with null after the delay.
6769
*/
6870
public function delay(float $seconds): PromiseInterface;
6971

@@ -73,8 +75,8 @@ public function delay(float $seconds): PromiseInterface;
7375
* Returns a promise that resolves with an array of all resolved values
7476
* in the same order as the input promises, or rejects with the first rejection.
7577
*
76-
* @param array $promises Array of PromiseInterface instances
77-
* @return PromiseInterface A promise that resolves with an array of results
78+
* @param array<PromiseInterface<mixed>> $promises Array of PromiseInterface instances.
79+
* @return PromiseInterface<array<mixed>> A promise that resolves with an array of results.
7880
*/
7981
public function all(array $promises): PromiseInterface;
8082

@@ -84,8 +86,8 @@ public function all(array $promises): PromiseInterface;
8486
* The returned promise will resolve or reject with the value/reason
8587
* of whichever input promise settles first.
8688
*
87-
* @param array $promises Array of PromiseInterface instances
88-
* @return PromiseInterface A promise that settles with the first settled promise
89+
* @param array<PromiseInterface<mixed>> $promises Array of PromiseInterface instances.
90+
* @return PromiseInterface<mixed> A promise that settles with the first settled promise.
8991
*/
9092
public function race(array $promises): PromiseInterface;
9193

@@ -95,9 +97,9 @@ public function race(array $promises): PromiseInterface;
9597
* Limits the number of simultaneously executing tasks while ensuring
9698
* all tasks eventually complete.
9799
*
98-
* @param array $tasks Array of callable tasks that return promises
99-
* @param int $concurrency Maximum number of concurrent executions (default: 10)
100-
* @return PromiseInterface A promise that resolves when all tasks complete
100+
* @param array<callable(): PromiseInterface<mixed>> $tasks Array of callable tasks that return promises.
101+
* @param int $concurrency Maximum number of concurrent executions (default: 10).
102+
* @return PromiseInterface<array<mixed>> A promise that resolves with an array of all results when all tasks complete.
101103
*/
102104
public function concurrent(array $tasks, int $concurrency = 10): PromiseInterface;
103105

@@ -107,10 +109,10 @@ public function concurrent(array $tasks, int $concurrency = 10): PromiseInterfac
107109
* This method processes tasks in smaller batches, allowing for
108110
* controlled concurrency and resource management.
109111
*
110-
* @param array $tasks Array of tasks (callables or promises) to execute
111-
* @param int $batchSize Size of each batch to process concurrently
112-
* @param int $concurrency Maximum number of concurrent executions per batch
113-
* @return PromiseInterface A promise that resolves with all results
112+
* @param array<callable(): PromiseInterface<mixed>> $tasks Array of tasks (callables that return promises) to execute.
113+
* @param int $batchSize Size of each batch to process concurrently.
114+
* @param int|null $concurrency Maximum number of concurrent executions per batch.
115+
* @return PromiseInterface<array<mixed>> A promise that resolves with all results.
114116
*/
115117
public function batch(array $tasks, int $batchSize = 10, ?int $concurrency = null): PromiseInterface;
116-
}
118+
}

src/Promise/Interfaces/PromiseInterface.php

Lines changed: 23 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,8 @@
22

33
namespace Rcalicdan\FiberAsync\Promise\Interfaces;
44

5+
use LogicException;
6+
57
/**
68
* Represents the eventual result of an asynchronous operation.
79
*
@@ -18,7 +20,8 @@ interface PromiseInterface
1820
* Once resolved, the promise cannot be resolved or rejected again.
1921
* All attached fulfillment handlers will be called with the value.
2022
*
21-
* @param mixed $value The value to resolve the promise with
23+
* @param TValue $value The value to resolve the promise with.
24+
* @return void
2225
*/
2326
public function resolve(mixed $value): void;
2427

@@ -28,21 +31,22 @@ public function resolve(mixed $value): void;
2831
* Once rejected, the promise cannot be resolved or rejected again.
2932
* All attached rejection handlers will be called with the reason.
3033
*
31-
* @param mixed $reason The reason for rejection (typically an exception or error message)
34+
* @param mixed $reason The reason for rejection (typically an exception or error message).
35+
* @return void
3236
*/
3337
public function reject(mixed $reason): void;
3438

3539
/**
3640
* Attaches handlers for promise fulfillment and/or rejection.
3741
*
3842
* Returns a new promise that will be resolved or rejected based on
39-
* the return value of the executed handler.
43+
* the return value of the executed handler. This allows for chaining and
44+
* transforming values.
4045
*
41-
* @param callable|null $onFulfilled Handler for successful resolution with signature:
42-
* function(mixed $value): mixed
43-
* @param callable|null $onRejected Handler for rejection with signature:
44-
* function(mixed $reason): mixed
45-
* @return PromiseInterface A new promise for method chaining
46+
* @template TResult
47+
* @param callable(TValue): (TResult|PromiseInterface<TResult>) $onFulfilled Handler for successful resolution.
48+
* @param callable(mixed): (TResult|PromiseInterface<TResult>) $onRejected Handler for rejection.
49+
* @return PromiseInterface<TResult> A new promise for method chaining.
4650
*/
4751
public function then(?callable $onFulfilled = null, ?callable $onRejected = null): PromiseInterface;
4852

@@ -51,9 +55,9 @@ public function then(?callable $onFulfilled = null, ?callable $onRejected = null
5155
*
5256
* Equivalent to calling then(null, $onRejected).
5357
*
54-
* @param callable $onRejected Handler for rejection with signature:
55-
* function(mixed $reason): mixed
56-
* @return PromiseInterface A new promise for method chaining
58+
* @template TResult
59+
* @param callable(mixed): (TResult|PromiseInterface<TResult>) $onRejected Handler for rejection.
60+
* @return PromiseInterface<TResult> A new promise for method chaining.
5761
*/
5862
public function catch(callable $onRejected): PromiseInterface;
5963

@@ -63,30 +67,28 @@ public function catch(callable $onRejected): PromiseInterface;
6367
* The finally handler receives no arguments and its return value
6468
* does not affect the promise chain unless it throws an exception.
6569
*
66-
* @param callable $onFinally Handler to execute after settlement with signature:
67-
* function(): mixed
68-
* @return PromiseInterface A new promise for method chaining
70+
* @return PromiseInterface<TValue> A new promise that will settle with the same outcome as the original.
6971
*/
7072
public function finally(callable $onFinally): PromiseInterface;
7173

7274
/**
7375
* Checks if the promise has been resolved with a value.
7476
*
75-
* @return bool True if resolved, false otherwise
77+
* @return bool True if resolved, false otherwise.
7678
*/
7779
public function isResolved(): bool;
7880

7981
/**
8082
* Checks if the promise has been rejected with a reason.
8183
*
82-
* @return bool True if rejected, false otherwise
84+
* @return bool True if rejected, false otherwise.
8385
*/
8486
public function isRejected(): bool;
8587

8688
/**
8789
* Checks if the promise is still pending (neither resolved nor rejected).
8890
*
89-
* @return bool True if pending, false otherwise
91+
* @return bool True if pending, false otherwise.
9092
*/
9193
public function isPending(): bool;
9294

@@ -96,9 +98,8 @@ public function isPending(): bool;
9698
* This method should only be called after confirming the promise
9799
* is resolved using isResolved().
98100
*
99-
* @return mixed The resolved value
100-
*
101-
* @throws \LogicException If called on a non-resolved promise
101+
* @return TValue The resolved value.
102+
* @throws LogicException If called on a non-resolved promise.
102103
*/
103104
public function getValue(): mixed;
104105

@@ -108,9 +109,8 @@ public function getValue(): mixed;
108109
* This method should only be called after confirming the promise
109110
* is rejected using isRejected().
110111
*
111-
* @return mixed The rejection reason
112-
*
113-
* @throws \LogicException If called on a non-rejected promise
112+
* @return mixed The rejection reason.
113+
* @throws LogicException If called on a non-rejected promise.
114114
*/
115115
public function getReason(): mixed;
116116
}

0 commit comments

Comments
 (0)