TODO added
[poolifier.git] / lib / workers.js
1 'use strict'
2 const {
3 isMainThread, parentPort
4 } = require('worker_threads')
5 const { AsyncResource } = require('async_hooks')
6 const maxInactiveTime = 1000 * 60
7
8 /**
9 * An example worker that will be always alive, you just need to extend this class if you want a static pool.<br>
10 * When this worker is inactive for more than 1 minute, it will send this info to the main thread,<br>
11 * if you are using DynamicThreadPool, the workers created after will be killed, the min num of thread will be guaranteed
12 * @author Alessandro Pio Ardizio
13 * @since 0.0.1
14 */
15 class ThreadWorker extends AsyncResource {
16 constructor (fn) {
17 super('worker-thread-pool:pioardi')
18 this.lastTask = Date.now()
19 if (!fn) throw new Error('Fn parameter is mandatory')
20 // keep the worker active
21 if (!isMainThread) {
22 this.interval = setInterval(this._checkAlive.bind(this), maxInactiveTime)
23 this._checkAlive.bind(this)()
24 }
25 parentPort.on('message', (value) => {
26 if (value && value._id) {
27 // here you will receive messages
28 // console.log('This is the main thread ' + isMainThread)
29 const res = this.runInAsyncScope(fn, null, value)
30 this.parent.postMessage({ data: res, _id: value._id })
31 this.lastTask = Date.now()
32 } else if (value.parent) {
33 // save the port to communicate with the main thread
34 // this will be received once
35 this.parent = value.parent
36 } else if (value.kill) {
37 // here is time to kill this thread, just clearing the interval
38 clearInterval(this.interval)
39 }
40 })
41 }
42
43 _checkAlive () {
44 if ((Date.now() - this.lastTask) > maxInactiveTime) {
45 this.parent.postMessage({ kill: 1 })
46 }
47 }
48 }
49
50 module.exports.ThreadWorker = ThreadWorker