X-Git-Url: https://git.piment-noir.org/?a=blobdiff_plain;f=src%2Fpools%2Fselection-strategies.ts;h=034b1612334abe6b83ad1943dd05857e7dad89b7;hb=bd0e5c4dda309d307e83ddfd8a974df631fc21da;hp=f86442b0f5fc836fd9cacf77333d1bab69f1fae2;hpb=ff5e76e152be8540cba8118bb4e2b9da314dfff5;p=poolifier.git diff --git a/src/pools/selection-strategies.ts b/src/pools/selection-strategies.ts index f86442b0..034b1612 100644 --- a/src/pools/selection-strategies.ts +++ b/src/pools/selection-strategies.ts @@ -1,6 +1,6 @@ -import { isKillBehavior, KillBehaviors } from '../worker/worker-options' import type { IWorker } from './abstract-pool' import type { IPoolInternal } from './pool-internal' +import { PoolType } from './pool-internal' /** * Enumeration of worker choice strategies. @@ -90,7 +90,7 @@ class LessRecentlyUsedWorkerChoiceStrategy< /** @inheritdoc */ public choose (): Worker { - const isPoolDynamic = this.pool.dynamic + const isPoolDynamic = this.pool.type === PoolType.DYNAMIC let minNumberOfTasks = Infinity // A worker is always found because it picks the one with fewer tasks let lessRecentlyUsedWorker!: Worker @@ -98,8 +98,8 @@ class LessRecentlyUsedWorkerChoiceStrategy< if (!isPoolDynamic && numberOfTasks === 0) { return worker } else if (numberOfTasks < minNumberOfTasks) { - minNumberOfTasks = numberOfTasks lessRecentlyUsedWorker = worker + minNumberOfTasks = numberOfTasks } } return lessRecentlyUsedWorker @@ -121,10 +121,12 @@ class DynamicPoolWorkerChoiceStrategy * Constructs a worker choice strategy for dynamical pools. * * @param pool The pool instance. - * @param workerChoiceStrategy The worker choice strategy when the pull is full. + * @param createDynamicallyWorkerCallback The worker creation callback for dynamic pool. + * @param workerChoiceStrategy The worker choice strategy when the pull is busy. */ public constructor ( private readonly pool: IPoolInternal, + private createDynamicallyWorkerCallback: () => Worker, workerChoiceStrategy: WorkerChoiceStrategy = WorkerChoiceStrategies.ROUND_ROBIN ) { this.workerChoiceStrategy = SelectionStrategiesUtils.getWorkerChoiceStrategy( @@ -135,31 +137,17 @@ class DynamicPoolWorkerChoiceStrategy /** @inheritdoc */ public choose (): Worker { - const freeWorker = SelectionStrategiesUtils.findFreeWorkerBasedOnTasks( - this.pool - ) - if (freeWorker) { - return freeWorker + const freeTaskMapEntry = this.pool.findFreeTasksMapEntry() + if (freeTaskMapEntry) { + return freeTaskMapEntry[0] } - if (this.pool.workers.length === this.pool.max) { - this.pool.emitter.emit('FullPool') + if (this.pool.busy) { return this.workerChoiceStrategy.choose() } // All workers are busy, create a new worker - const workerCreated = this.pool.createAndSetupWorker() - this.pool.registerWorkerMessageListener(workerCreated, message => { - const tasksInProgress = this.pool.tasks.get(workerCreated) - if ( - isKillBehavior(KillBehaviors.HARD, message.kill) || - tasksInProgress === 0 - ) { - // Kill received from the worker, means that no new tasks are submitted to that worker for a while ( > maxInactiveTime) - void this.pool.destroyWorker(workerCreated) - } - }) - return workerCreated + return this.createDynamicallyWorkerCallback() } } @@ -182,10 +170,12 @@ export class WorkerChoiceStrategyContext< * Worker choice strategy context constructor. * * @param pool The pool instance. + * @param createDynamicallyWorkerCallback The worker creation callback for dynamic pool. * @param workerChoiceStrategy The worker choice strategy. */ public constructor ( private readonly pool: IPoolInternal, + private createDynamicallyWorkerCallback: () => Worker, workerChoiceStrategy: WorkerChoiceStrategy = WorkerChoiceStrategies.ROUND_ROBIN ) { this.setWorkerChoiceStrategy(workerChoiceStrategy) @@ -200,9 +190,10 @@ export class WorkerChoiceStrategyContext< private getPoolWorkerChoiceStrategy ( workerChoiceStrategy: WorkerChoiceStrategy = WorkerChoiceStrategies.ROUND_ROBIN ): IWorkerChoiceStrategy { - if (this.pool.dynamic) { + if (this.pool.type === PoolType.DYNAMIC) { return new DynamicPoolWorkerChoiceStrategy( this.pool, + this.createDynamicallyWorkerCallback, workerChoiceStrategy ) } @@ -236,33 +227,9 @@ export class WorkerChoiceStrategyContext< } /** - * Worker selection strategies helpers. + * Worker selection strategies helpers class. */ class SelectionStrategiesUtils { - /** - * Find a free worker based on number of tasks the worker has applied. - * - * If a worker was found that has `0` tasks, it is detected as free and will be returned. - * - * If no free worker was found, `null` will be returned. - * - * @param pool The pool instance. - * @returns A free worker if there was one, otherwise `null`. - */ - public static findFreeWorkerBasedOnTasks< - Worker extends IWorker, - Data, - Response - > (pool: IPoolInternal): Worker | null { - for (const [worker, numberOfTasks] of pool.tasks) { - if (numberOfTasks === 0) { - // A worker is free, use it - return worker - } - } - return null - } - /** * Get the worker choice strategy instance. *