The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
+## [2.2.1] - 2022-05-01
+
+-
+
## [2.2.0] - 2022-05-01
### Breaking Changes
})
}
+function jsonIntegerSerialization (n) {
+ for (let i = 0; i < n; i++) {
+ const o = {
+ a: i
+ }
+ JSON.stringify(o)
+ }
+}
+
function generateRandomInteger (max, min = 0) {
max = Math.floor(max)
if (min) {
return Math.floor(Math.random() * (max + 1))
}
+/**
+ * Intentionally inefficient implementation.
+ *
+ * @param {*} n
+ * @returns {number}
+ */
+function fibonacci (n) {
+ if (n <= 1) return 1
+ return fibonacci(n - 1) + fibonacci(n - 2)
+}
+
const LIST_FORMATTER = new Intl.ListFormat('en-US', {
style: 'long',
type: 'conjunction'
})
-module.exports = { generateRandomInteger, LIST_FORMATTER, runPoolifierTest }
+module.exports = {
+ runPoolifierTest,
+ jsonIntegerSerialization,
+ generateRandomInteger,
+ fibonacci,
+ LIST_FORMATTER
+}
'use strict'
const { ClusterWorker } = require('../../../lib/index')
+const { jsonIntegerSerialization } = require('../benchmark-utils')
function yourFunction (data) {
- for (let i = 0; i < 1000; i++) {
- const o = {
- a: i
- }
- JSON.stringify(o)
- }
+ jsonIntegerSerialization(1000)
// console.log('This is the main thread ' + isMaster)
return { ok: 1 }
}
'use strict'
const { ThreadWorker } = require('../../../lib/index')
+const { jsonIntegerSerialization } = require('../benchmark-utils')
function yourFunction (data) {
- for (let i = 0; i < 1000; i++) {
- const o = {
- a: i
- }
- JSON.stringify(o)
- }
+ jsonIntegerSerialization(1000)
// console.log('This is the main thread ' + isMainThread)
return { ok: 1 }
}
() => {
const workerCreated = this.createAndSetupWorker()
this.registerWorkerMessageListener(workerCreated, message => {
- const tasksInProgress = this.tasks.get(workerCreated)
if (
isKillBehavior(KillBehaviors.HARD, message.kill) ||
- tasksInProgress === 0
+ this.tasks.get(workerCreated) === 0
) {
// Kill received from the worker, means that no new tasks are submitted to that worker for a while ( > maxInactiveTime)
this.destroyWorker(workerCreated) as void
const messageId = ++this.nextMessageId
const res = this.internalExecute(worker, messageId)
this.checkAndEmitBusy()
- this.sendToWorker(worker, { data: data || ({} as Data), id: messageId })
+ this.sendToWorker(worker, { data: data ?? ({} as Data), id: messageId })
return res
}
* @returns New, completely set up worker.
*/
protected createAndSetupWorker (): Worker {
- const worker: Worker = this.createWorker()
+ const worker = this.createWorker()
worker.on('message', this.opts.messageHandler ?? EMPTY_FUNCTION)
worker.on('error', this.opts.errorHandler ?? EMPTY_FUNCTION)
/**
* This function is the listener registered for each worker.
*
- * @returns The listener function to execute when a message is sent from a worker.
+ * @returns The listener function to execute when a message is received from a worker.
*/
protected workerListener (): (message: MessageValue<Response>) => void {
return message => {
- if (message.id) {
- const value = this.promiseMap.get(message.id)
- if (value) {
- this.decreaseWorkersTasks(value.worker)
- if (message.error) value.reject(message.error)
- else value.resolve(message.data as Response)
+ if (message.id !== undefined) {
+ const promise = this.promiseMap.get(message.id)
+ if (promise !== undefined) {
+ this.decreaseWorkersTasks(promise.worker)
+ if (message.error) promise.reject(message.error)
+ else promise.resolve(message.data as Response)
this.promiseMap.delete(message.id)
}
}
it('Shutdown test', async () => {
const exitPromise = TestUtils.waitExits(pool, min)
await pool.destroy()
- const res = await exitPromise
- expect(res).toBe(min)
+ const numberOfExitEvents = await exitPromise
+ expect(numberOfExitEvents).toBe(min)
})
it('Validation of inputs test', () => {
it('Shutdown test', async () => {
const exitPromise = TestUtils.waitExits(pool, numberOfWorkers)
await pool.destroy()
- const res = await exitPromise
- expect(res).toBe(numberOfWorkers)
+ const numberOfExitEvents = await exitPromise
+ expect(numberOfExitEvents).toBe(numberOfWorkers)
})
it('Should work even without opts in input', async () => {
// The `busy` event is triggered when the number of submitted tasks at once reach the max number of workers in the dynamic pool.
// So in total numberOfWorkers + 1 times for a loop submitting up to numberOfWorkers * 2 tasks to the dynamic pool.
expect(poolBusy).toBe(max + 1)
- const res = await TestUtils.waitExits(pool, max - min)
- expect(res).toBe(max - min)
+ const numberOfExitEvents = await TestUtils.waitExits(pool, max - min)
+ expect(numberOfExitEvents).toBe(max - min)
})
it('Verify scale thread up and down is working', async () => {
it('Shutdown test', async () => {
const exitPromise = TestUtils.waitExits(pool, numberOfThreads)
await pool.destroy()
- const res = await exitPromise
- expect(res).toBe(numberOfThreads)
+ const numberOfExitEvents = await exitPromise
+ expect(numberOfExitEvents).toBe(numberOfThreads)
})
it('Should work even without opts in input', async () => {
static async sleep (ms) {
return new Promise(resolve => setTimeout(resolve, ms))
}
+
+ static async workerSleepFunction (data, ms) {
+ return new Promise((resolve, reject) => {
+ setTimeout(() => resolve(data), ms)
+ })
+ }
+
+ static jsonIntegerSerialization (n) {
+ for (let i = 0; i < n; i++) {
+ const o = {
+ a: i
+ }
+ JSON.stringify(o)
+ }
+ }
+
+ /**
+ * Intentionally inefficient implementation.
+ *
+ * @param {*} n
+ * @returns {number}
+ */
+ static fibonacci (n) {
+ if (n <= 1) return 1
+ return TestUtils.fibonacci(n - 1) + TestUtils.fibonacci(n - 2)
+ }
+
+ /**
+ * Intentionally inefficient implementation.
+ *
+ * @param {*} n
+ * @returns {number}
+ */
+ static factorial (n) {
+ if (n === 0) {
+ return 1
+ } else {
+ return TestUtils.factorial(n - 1) * n
+ }
+ }
}
module.exports = TestUtils
'use strict'
const { ClusterWorker, KillBehaviors } = require('../../../lib/index')
+const TestUtils = require('../../test-utils')
async function sleep (data) {
- return new Promise((resolve, reject) => {
- setTimeout(() => resolve(data), 2000)
- })
+ return TestUtils.workerSleepFunction(data, 2000)
}
module.exports = new ClusterWorker(sleep, {
'use strict'
const { ClusterWorker, KillBehaviors } = require('../../../lib/index')
+const TestUtils = require('../../test-utils')
async function sleep (data) {
- return new Promise((resolve, reject) => {
- setTimeout(() => resolve(data), 50000)
- })
+ return TestUtils.workerSleepFunction(data, 50000)
}
module.exports = new ClusterWorker(sleep, {
'use strict'
const { ClusterWorker } = require('../../../lib/index')
+const TestUtils = require('../../test-utils')
async function sleep (data) {
- return new Promise((resolve, reject) => {
- setTimeout(() => resolve(data), 50000)
- })
+ return TestUtils.workerSleepFunction(data, 50000)
}
module.exports = new ClusterWorker(sleep, {
'use strict'
const { ClusterWorker, KillBehaviors } = require('../../../lib/index')
const { isMaster } = require('cluster')
+const TestUtils = require('../../test-utils')
function test (data) {
- for (let i = 0; i < 50; i++) {
- const o = {
- a: i
- }
- JSON.stringify(o)
- }
+ TestUtils.jsonIntegerSerialization(50)
return isMaster
}
'use strict'
const { ThreadWorker, KillBehaviors } = require('../../../lib/index')
+const TestUtils = require('../../test-utils')
async function sleep (data) {
- return new Promise((resolve, reject) => {
- setTimeout(() => resolve(data), 2000)
- })
+ return TestUtils.workerSleepFunction(data, 2000)
}
module.exports = new ThreadWorker(sleep, {
'use strict'
const { ThreadWorker, KillBehaviors } = require('../../../lib/index')
+const TestUtils = require('../../test-utils')
async function sleep (data) {
- return new Promise((resolve, reject) => {
- setTimeout(() => resolve(data), 50000)
- })
+ return TestUtils.workerSleepFunction(data, 50000)
}
module.exports = new ThreadWorker(sleep, {