1414use ReactParallel \Contracts \LowLevelPoolInterface ;
1515use ReactParallel \EventLoop \EventLoopBridge ;
1616use ReactParallel \Runtime \Runtime ;
17+ use WyriHaximus \Metrics \Label ;
1718use WyriHaximus \PoolInfo \Info ;
1819
1920use function array_key_exists ;
2223use function count ;
2324use function dirname ;
2425use function file_exists ;
26+ use function hrtime ;
2527use function is_string ;
2628use function React \Promise \reject ;
2729use function spl_object_hash ;
@@ -51,6 +53,8 @@ final class Infinite implements LowLevelPoolInterface
5153
5254 private float $ ttl ;
5355
56+ private ?Metrics $ metrics = null ;
57+
5458 /** @var GroupInterface[] */
5559 private array $ groups = [];
5660
@@ -71,6 +75,14 @@ public function __construct(LoopInterface $loop, EventLoopBridge $eventLoopBridg
7175 $ this ->eventLoopBridge = $ eventLoopBridge ;
7276 }
7377
78+ public function withMetrics (Metrics $ metrics ): self
79+ {
80+ $ self = clone $ this ;
81+ $ self ->metrics = $ metrics ;
82+
83+ return $ self ;
84+ }
85+
7486 /**
7587 * @param mixed[] $args
7688 */
@@ -89,8 +101,21 @@ public function run(Closure $callable, array $args = []): PromiseInterface
89101
90102 $ resolve ($ this ->getIdleRuntime ());
91103 }))->then (function (Runtime $ runtime ) use ($ callable , $ args ): PromiseInterface {
104+ $ time = null ;
105+ if ($ this ->metrics instanceof Metrics) {
106+ $ this ->metrics ->threads ()->gauge (new Label ('state ' , 'busy ' ))->incr ();
107+ $ this ->metrics ->threads ()->gauge (new Label ('state ' , 'idle ' ))->dcr ();
108+ $ time = hrtime (true );
109+ }
110+
92111 /** @psalm-suppress UndefinedInterfaceMethod */
93- return $ runtime ->run ($ callable , $ args )->always (function () use ($ runtime ): void {
112+ return $ runtime ->run ($ callable , $ args )->always (function () use ($ runtime , $ time ): void {
113+ if ($ this ->metrics instanceof Metrics) {
114+ $ this ->metrics ->executionTime ()->summary ()->observe ((hrtime (true ) - $ time ) / 1e+9 );
115+ $ this ->metrics ->threads ()->gauge (new Label ('state ' , 'idle ' ))->incr ();
116+ $ this ->metrics ->threads ()->gauge (new Label ('state ' , 'busy ' ))->dcr ();
117+ }
118+
94119 if ($ this ->ttl >= 0.1 ) {
95120 $ this ->addRuntimeToIdleList ($ runtime );
96121 $ this ->startTtlTimer ($ runtime );
@@ -182,6 +207,10 @@ private function spawnRuntime(): Runtime
182207 $ runtime = new Runtime ($ this ->eventLoopBridge , $ this ->autoload );
183208 $ this ->runtimes [spl_object_hash ($ runtime )] = $ runtime ;
184209
210+ if ($ this ->metrics instanceof Metrics) {
211+ $ this ->metrics ->threads ()->gauge (new Label ('state ' , 'idle ' ))->incr ();
212+ }
213+
185214 return $ runtime ;
186215 }
187216
@@ -205,6 +234,10 @@ private function closeRuntime(string $hash): void
205234 unset($ this ->idleRuntimes [$ hash ]);
206235 }
207236
237+ if ($ this ->metrics instanceof Metrics) {
238+ $ this ->metrics ->threads ()->gauge (new Label ('state ' , 'idle ' ))->dcr ();
239+ }
240+
208241 if (! array_key_exists ($ hash , $ this ->ttlTimers )) {
209242 return ;
210243 }
0 commit comments