X-Git-Url: https://git.piment-noir.org/?a=blobdiff_plain;f=tests%2Fpools%2Fselection-strategies%2Fselection-strategies.test.js;h=b2aa4a0b69fbd4e006ce6f53fecb90295edb535d;hb=f59e102739e13698f278f1d9d58ab26ed8150442;hp=94263ab49da7eb191206b399fc00876dd5115fd7;hpb=802983837716dc38305c13f905a1977688365293;p=poolifier.git diff --git a/tests/pools/selection-strategies/selection-strategies.test.js b/tests/pools/selection-strategies/selection-strategies.test.js index 94263ab4..b2aa4a0b 100644 --- a/tests/pools/selection-strategies/selection-strategies.test.js +++ b/tests/pools/selection-strategies/selection-strategies.test.js @@ -15,10 +15,14 @@ describe('Selection strategies test suite', () => { expect(WorkerChoiceStrategies.ROUND_ROBIN).toBe('ROUND_ROBIN') expect(WorkerChoiceStrategies.LEAST_USED).toBe('LEAST_USED') expect(WorkerChoiceStrategies.LEAST_BUSY).toBe('LEAST_BUSY') + expect(WorkerChoiceStrategies.LEAST_ELU).toBe('LEAST_ELU') expect(WorkerChoiceStrategies.FAIR_SHARE).toBe('FAIR_SHARE') expect(WorkerChoiceStrategies.WEIGHTED_ROUND_ROBIN).toBe( 'WEIGHTED_ROUND_ROBIN' ) + expect(WorkerChoiceStrategies.INTERLEAVED_WEIGHTED_ROUND_ROBIN).toBe( + 'INTERLEAVED_WEIGHTED_ROUND_ROBIN' + ) }) it('Verify ROUND_ROBIN strategy is the default at pool creation', async () => { @@ -94,7 +98,7 @@ describe('Selection strategies test suite', () => { expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( workerChoiceStrategy - ).currentWorkerNodeId + ).nextWorkerNodeId ).toBe(0) expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -111,7 +115,31 @@ describe('Selection strategies test suite', () => { await pool.destroy() }) - it('Verify ROUND_ROBIN strategy default tasks usage statistics requirements', async () => { + it('Verify ROUND_ROBIN strategy default policy', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.ROUND_ROBIN + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: true + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: true + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify ROUND_ROBIN strategy default tasks statistics requirements', async () => { const workerChoiceStrategy = WorkerChoiceStrategies.ROUND_ROBIN let pool = new FixedThreadPool( max, @@ -119,14 +147,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: false, - avgRunTime: false, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) await pool.destroy() pool = new DynamicThreadPool( @@ -136,14 +173,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: false, - avgRunTime: false, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) // We need to clean up the resources after our test await pool.destroy() @@ -156,10 +202,55 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.ROUND_ROBIN } ) // TODO: Create a better test to cover `RoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: maxMultiplier, + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + } + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + WorkerChoiceStrategies.ROUND_ROBIN + ).nextWorkerNodeId + ).toBe(0) // We need to clean up the resources after our test await pool.destroy() }) @@ -172,10 +263,55 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.ROUND_ROBIN } ) // TODO: Create a better test to cover `RoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: maxMultiplier, + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) } + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + WorkerChoiceStrategies.ROUND_ROBIN + ).nextWorkerNodeId + ).toBe(0) // We need to clean up the resources after our test await pool.destroy() }) @@ -246,7 +382,31 @@ describe('Selection strategies test suite', () => { await pool.destroy() }) - it('Verify LEAST_USED strategy default tasks usage statistics requirements', async () => { + it('Verify LEAST_USED strategy default policy', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.LEAST_USED + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify LEAST_USED strategy default tasks statistics requirements', async () => { const workerChoiceStrategy = WorkerChoiceStrategies.LEAST_USED let pool = new FixedThreadPool( max, @@ -254,14 +414,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: false, - avgRunTime: false, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) await pool.destroy() pool = new DynamicThreadPool( @@ -271,14 +440,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: false, - avgRunTime: false, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) // We need to clean up the resources after our test await pool.destroy() @@ -291,9 +469,53 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.LEAST_USED } ) // TODO: Create a better test to cover `LeastUsedWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) } // We need to clean up the resources after our test await pool.destroy() @@ -307,15 +529,83 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.LEAST_USED } ) // TODO: Create a better test to cover `LeastUsedWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) } // We need to clean up the resources after our test await pool.destroy() }) - it('Verify LEAST_BUSY strategy default tasks usage statistics requirements', async () => { + it('Verify LEAST_BUSY strategy default policy', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.LEAST_BUSY + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify LEAST_BUSY strategy default tasks statistics requirements', async () => { const workerChoiceStrategy = WorkerChoiceStrategies.LEAST_BUSY let pool = new FixedThreadPool( max, @@ -323,14 +613,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: true, - avgRunTime: false, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: true, + average: false, + median: false + }, + waitTime: { + aggregate: true, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) await pool.destroy() pool = new DynamicThreadPool( @@ -340,14 +639,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: true, - avgRunTime: false, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: true, + average: false, + median: false + }, + waitTime: { + aggregate: true, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) // We need to clean up the resources after our test await pool.destroy() @@ -360,9 +668,55 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.LEAST_BUSY } ) // TODO: Create a better test to cover `LeastBusyWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: expect.any(Number), + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.waitTime.aggregate).toBeGreaterThanOrEqual(0) } // We need to clean up the resources after our test await pool.destroy() @@ -376,15 +730,288 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.LEAST_BUSY } ) // TODO: Create a better test to cover `LeastBusyWorkerChoiceStrategy#choose` + const promises = new Set() + const maxMultiplier = 2 + for (let i = 0; i < max * maxMultiplier; i++) { + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: expect.any(Number), + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.waitTime.aggregate).toBeGreaterThanOrEqual(0) + } + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify LEAST_ELU strategy default policy', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.LEAST_ELU + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify LEAST_ELU strategy default tasks statistics requirements', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.LEAST_ELU + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect( + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() + ).toStrictEqual({ + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: true, + average: false, + median: false + } + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect( + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() + ).toStrictEqual({ + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: true, + average: false, + median: false + } + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify LEAST_ELU strategy can be run in a fixed pool', async () => { + const pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy: WorkerChoiceStrategies.LEAST_ELU } + ) + // TODO: Create a better test to cover `LeastEluWorkerChoiceStrategy#choose` + const promises = new Set() + const maxMultiplier = 2 + for (let i = 0; i < max * maxMultiplier; i++) { + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: expect.any(Number), + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: expect.any(Number) + } + }) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.elu.utilization).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeLessThanOrEqual(1) + } + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify LEAST_ELU strategy can be run in a dynamic pool', async () => { + const pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy: WorkerChoiceStrategies.LEAST_ELU } + ) + // TODO: Create a better test to cover `LeastEluWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: expect.any(Number), + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: expect.any(Number) + } + }) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.elu.utilization).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeLessThanOrEqual(1) } // We need to clean up the resources after our test await pool.destroy() }) - it('Verify FAIR_SHARE strategy default tasks usage statistics requirements', async () => { + it('Verify FAIR_SHARE strategy default policy', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.FAIR_SHARE + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: false + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify FAIR_SHARE strategy default tasks statistics requirements', async () => { const workerChoiceStrategy = WorkerChoiceStrategies.FAIR_SHARE let pool = new FixedThreadPool( max, @@ -392,14 +1019,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: true, - avgRunTime: true, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: true, + average: true, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: true, + average: true, + median: false + } }) await pool.destroy() pool = new DynamicThreadPool( @@ -409,14 +1045,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: true, - avgRunTime: true, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: true, + average: true, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: true, + average: true, + median: false + } }) // We need to clean up the resources after our test await pool.destroy() @@ -429,25 +1074,57 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.FAIR_SHARE } ) // TODO: Create a better test to cover `FairShareChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) for (const workerNode of pool.workerNodes) { - expect(workerNode.tasksUsage).toStrictEqual({ - run: maxMultiplier, - running: 0, - runTime: expect.any(Number), - runTimeHistory: expect.any(CircularArray), - avgRunTime: expect.any(Number), - medRunTime: 0, - waitTime: 0, - waitTimeHistory: expect.any(CircularArray), - avgWaitTime: 0, - medWaitTime: 0, - error: 0 + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + utilization: expect.any(Number) + } }) - expect(workerNode.tasksUsage.avgRunTime).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.runTime.average).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeLessThanOrEqual(1) } expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -466,25 +1143,57 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.FAIR_SHARE } ) // TODO: Create a better test to cover `FairShareChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) for (const workerNode of pool.workerNodes) { - expect(workerNode.tasksUsage).toStrictEqual({ - run: max * maxMultiplier, - running: 0, - runTime: expect.any(Number), - runTimeHistory: expect.any(CircularArray), - avgRunTime: expect.any(Number), - medRunTime: 0, - waitTime: 0, - waitTimeHistory: expect.any(CircularArray), - avgWaitTime: 0, - medWaitTime: 0, - error: 0 + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + utilization: expect.any(Number) + } }) - expect(workerNode.tasksUsage.avgRunTime).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.runTime.average).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeLessThanOrEqual(1) } expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -503,30 +1212,62 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.FAIR_SHARE, workerChoiceStrategyOptions: { - medRunTime: true + runTime: { median: true } } } ) // TODO: Create a better test to cover `FairShareChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) for (const workerNode of pool.workerNodes) { - expect(workerNode.tasksUsage).toStrictEqual({ - run: max * maxMultiplier, - running: 0, - runTime: expect.any(Number), - runTimeHistory: expect.any(CircularArray), - avgRunTime: 0, - medRunTime: expect.any(Number), - waitTime: 0, - waitTimeHistory: expect.any(CircularArray), - avgWaitTime: 0, - medWaitTime: 0, - error: 0 + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: 0, + median: expect.any(Number), + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + utilization: expect.any(Number) + } }) - expect(workerNode.tasksUsage.medRunTime).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.runTime.median).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.elu.utilization).toBeLessThanOrEqual(1) } expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -611,7 +1352,31 @@ describe('Selection strategies test suite', () => { await pool.destroy() }) - it('Verify WEIGHTED_ROUND_ROBIN strategy default tasks usage statistics requirements', async () => { + it('Verify WEIGHTED_ROUND_ROBIN strategy default policy', async () => { + const workerChoiceStrategy = WorkerChoiceStrategies.WEIGHTED_ROUND_ROBIN + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: true + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: true + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify WEIGHTED_ROUND_ROBIN strategy default tasks statistics requirements', async () => { const workerChoiceStrategy = WorkerChoiceStrategies.WEIGHTED_ROUND_ROBIN let pool = new FixedThreadPool( max, @@ -619,14 +1384,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: true, - avgRunTime: true, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: true, + average: true, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) await pool.destroy() pool = new DynamicThreadPool( @@ -636,14 +1410,23 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy } ) expect( - pool.workerChoiceStrategyContext.getRequiredStatistics() + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() ).toStrictEqual({ - runTime: true, - avgRunTime: true, - medRunTime: false, - waitTime: false, - avgWaitTime: false, - medWaitTime: false + runTime: { + aggregate: true, + average: true, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } }) // We need to clean up the resources after our test await pool.destroy() @@ -656,27 +1439,55 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.WEIGHTED_ROUND_ROBIN } ) // TODO: Create a better test to cover `WeightedRoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) for (const workerNode of pool.workerNodes) { - expect(workerNode.tasksUsage).toStrictEqual({ - // FIXME: it should be: - // run: max * maxMultiplier, - run: expect.any(Number), - running: 0, - runTime: expect.any(Number), - runTimeHistory: expect.any(CircularArray), - avgRunTime: expect.any(Number), - medRunTime: 0, - waitTime: 0, - waitTimeHistory: expect.any(CircularArray), - avgWaitTime: 0, - medWaitTime: 0, - error: 0 + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } }) - expect(workerNode.tasksUsage.avgRunTime).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.runTime.average).toBeGreaterThanOrEqual(0) } expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -700,25 +1511,55 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.WEIGHTED_ROUND_ROBIN } ) // TODO: Create a better test to cover `WeightedRoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) for (const workerNode of pool.workerNodes) { - expect(workerNode.tasksUsage).toStrictEqual({ - run: max * maxMultiplier, - running: 0, - runTime: expect.any(Number), - runTimeHistory: expect.any(CircularArray), - avgRunTime: expect.any(Number), - medRunTime: 0, - waitTime: 0, - waitTimeHistory: expect.any(CircularArray), - avgWaitTime: 0, - medWaitTime: 0, - error: 0 + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: expect.any(Number), + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } }) - expect(workerNode.tasksUsage.avgRunTime).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThan(0) + expect(workerNode.usage.runTime.average).toBeGreaterThan(0) } expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -742,30 +1583,60 @@ describe('Selection strategies test suite', () => { { workerChoiceStrategy: WorkerChoiceStrategies.WEIGHTED_ROUND_ROBIN, workerChoiceStrategyOptions: { - medRunTime: true + runTime: { median: true } } } ) // TODO: Create a better test to cover `WeightedRoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() const maxMultiplier = 2 for (let i = 0; i < max * maxMultiplier; i++) { - await pool.execute() + promises.add(pool.execute()) } + await Promise.all(promises) for (const workerNode of pool.workerNodes) { - expect(workerNode.tasksUsage).toStrictEqual({ - run: max * maxMultiplier, - running: 0, - runTime: expect.any(Number), - runTimeHistory: expect.any(CircularArray), - avgRunTime: 0, - medRunTime: expect.any(Number), - waitTime: 0, - waitTimeHistory: expect.any(CircularArray), - avgWaitTime: 0, - medWaitTime: 0, - error: 0 + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: expect.any(Number), + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: expect.any(Number), + average: 0, + median: expect.any(Number), + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } }) - expect(workerNode.tasksUsage.medRunTime).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeGreaterThanOrEqual(0) + expect(workerNode.usage.tasks.executed).toBeLessThanOrEqual( + max * maxMultiplier + ) + expect(workerNode.usage.runTime.aggregate).toBeGreaterThan(0) + expect(workerNode.usage.runTime.median).toBeGreaterThan(0) } expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -790,7 +1661,7 @@ describe('Selection strategies test suite', () => { expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( workerChoiceStrategy - ).currentWorkerNodeId + ).nextWorkerNodeId ).toBeDefined() expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -806,7 +1677,7 @@ describe('Selection strategies test suite', () => { expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( pool.workerChoiceStrategyContext.workerChoiceStrategy - ).currentWorkerNodeId + ).nextWorkerNodeId ).toBe(0) expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -827,7 +1698,7 @@ describe('Selection strategies test suite', () => { expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( workerChoiceStrategy - ).currentWorkerNodeId + ).nextWorkerNodeId ).toBeDefined() expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -843,7 +1714,7 @@ describe('Selection strategies test suite', () => { expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( pool.workerChoiceStrategyContext.workerChoiceStrategy - ).currentWorkerNodeId + ).nextWorkerNodeId ).toBe(0) expect( pool.workerChoiceStrategyContext.workerChoiceStrategies.get( @@ -859,6 +1730,355 @@ describe('Selection strategies test suite', () => { await pool.destroy() }) + it('Verify INTERLEAVED_WEIGHTED_ROUND_ROBIN strategy default policy', async () => { + const workerChoiceStrategy = + WorkerChoiceStrategies.INTERLEAVED_WEIGHTED_ROUND_ROBIN + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: true + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect(pool.workerChoiceStrategyContext.getStrategyPolicy()).toStrictEqual({ + useDynamicWorker: true + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify INTERLEAVED_WEIGHTED_ROUND_ROBIN strategy default tasks statistics requirements', async () => { + const workerChoiceStrategy = + WorkerChoiceStrategies.INTERLEAVED_WEIGHTED_ROUND_ROBIN + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect( + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() + ).toStrictEqual({ + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } + }) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { workerChoiceStrategy } + ) + expect( + pool.workerChoiceStrategyContext.getTaskStatisticsRequirements() + ).toStrictEqual({ + runTime: { + aggregate: false, + average: false, + median: false + }, + waitTime: { + aggregate: false, + average: false, + median: false + }, + elu: { + aggregate: false, + average: false, + median: false + } + }) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify INTERLEAVED_WEIGHTED_ROUND_ROBIN strategy can be run in a fixed pool', async () => { + const pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js', + { + workerChoiceStrategy: + WorkerChoiceStrategies.INTERLEAVED_WEIGHTED_ROUND_ROBIN + } + ) + // TODO: Create a better test to cover `InterleavedWeightedRoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() + const maxMultiplier = 2 + for (let i = 0; i < max * maxMultiplier; i++) { + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: maxMultiplier, + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + } + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ).toBeGreaterThan(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).roundId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).nextWorkerNodeId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).roundWeights + ).toStrictEqual([ + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ]) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify INTERLEAVED_WEIGHTED_ROUND_ROBIN strategy can be run in a dynamic pool', async () => { + const pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js', + { + workerChoiceStrategy: + WorkerChoiceStrategies.INTERLEAVED_WEIGHTED_ROUND_ROBIN + } + ) + // TODO: Create a better test to cover `InterleavedWeightedRoundRobinWorkerChoiceStrategy#choose` + const promises = new Set() + const maxMultiplier = 2 + for (let i = 0; i < max * maxMultiplier; i++) { + promises.add(pool.execute()) + } + await Promise.all(promises) + for (const workerNode of pool.workerNodes) { + expect(workerNode.usage).toStrictEqual({ + tasks: { + executed: maxMultiplier, + executing: 0, + queued: 0, + maxQueued: 0, + failed: 0 + }, + runTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + waitTime: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + elu: { + idle: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + active: { + aggregate: 0, + average: 0, + median: 0, + history: expect.any(CircularArray) + }, + utilization: 0 + } + }) + } + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ).toBeGreaterThan(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).roundId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).nextWorkerNodeId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).roundWeights + ).toStrictEqual([ + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ]) + // We need to clean up the resources after our test + await pool.destroy() + }) + + it('Verify INTERLEAVED_WEIGHTED_ROUND_ROBIN strategy internals are resets after setting it', async () => { + const workerChoiceStrategy = + WorkerChoiceStrategies.INTERLEAVED_WEIGHTED_ROUND_ROBIN + let pool = new FixedThreadPool( + max, + './tests/worker-files/thread/testWorker.js' + ) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundId + ).toBeDefined() + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).nextWorkerNodeId + ).toBeDefined() + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).defaultWorkerWeight + ).toBeDefined() + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundWeights + ).toBeDefined() + pool.setWorkerChoiceStrategy(workerChoiceStrategy) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).nextWorkerNodeId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ).toBeGreaterThan(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundWeights + ).toStrictEqual([ + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ]) + await pool.destroy() + pool = new DynamicThreadPool( + min, + max, + './tests/worker-files/thread/testWorker.js' + ) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundId + ).toBeDefined() + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).nextWorkerNodeId + ).toBeDefined() + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).defaultWorkerWeight + ).toBeDefined() + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundWeights + ).toBeDefined() + pool.setWorkerChoiceStrategy(workerChoiceStrategy) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).nextWorkerNodeId + ).toBe(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ).toBeGreaterThan(0) + expect( + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + workerChoiceStrategy + ).roundWeights + ).toStrictEqual([ + pool.workerChoiceStrategyContext.workerChoiceStrategies.get( + pool.workerChoiceStrategyContext.workerChoiceStrategy + ).defaultWorkerWeight + ]) + // We need to clean up the resources after our test + await pool.destroy() + }) + it('Verify unknown strategy throw error', () => { expect( () =>