|
| 1 | +import { dirname, resolve } from 'node:path' |
| 2 | +import { Tinypool } from 'tinypool' |
| 3 | +import { fileURLToPath } from 'node:url' |
| 4 | +import { MessageChannel } from 'node:worker_threads' |
| 5 | + |
| 6 | +const __dirname = dirname(fileURLToPath(import.meta.url)) |
| 7 | + |
| 8 | +test('isolated workers call teardown on worker recycle', async () => { |
| 9 | + const pool = new Tinypool({ |
| 10 | + filename: resolve(__dirname, 'fixtures/teardown.mjs'), |
| 11 | + minThreads: 1, |
| 12 | + maxThreads: 1, |
| 13 | + isolateWorkers: true, |
| 14 | + teardown: 'namedTeardown', |
| 15 | + }) |
| 16 | + |
| 17 | + for (const _ of [1, 2, 3, 4, 5]) { |
| 18 | + const { port1, port2 } = new MessageChannel() |
| 19 | + const promise = new Promise((resolve) => port2.on('message', resolve)) |
| 20 | + |
| 21 | + const output = await pool.run({ port: port1 }, { transferList: [port1] }) |
| 22 | + expect(output).toBe('Output of task #1') |
| 23 | + |
| 24 | + await expect(promise).resolves.toBe('Teardown of task #1') |
| 25 | + } |
| 26 | +}) |
| 27 | + |
| 28 | +test('non-isolated workers call teardown on worker recycle', async () => { |
| 29 | + const pool = new Tinypool({ |
| 30 | + filename: resolve(__dirname, 'fixtures/teardown.mjs'), |
| 31 | + minThreads: 1, |
| 32 | + maxThreads: 1, |
| 33 | + isolateWorkers: false, |
| 34 | + teardown: 'namedTeardown', |
| 35 | + }) |
| 36 | + |
| 37 | + function unexpectedTeardown(message: string) { |
| 38 | + assert.fail( |
| 39 | + `Teardown should not have been called yet. Received "${message}"` |
| 40 | + ) |
| 41 | + } |
| 42 | + |
| 43 | + const { port1, port2 } = new MessageChannel() |
| 44 | + |
| 45 | + for (const index of [1, 2, 3, 4, 5]) { |
| 46 | + port2.on('message', unexpectedTeardown) |
| 47 | + |
| 48 | + const transferList = index === 1 ? [port1] : [] |
| 49 | + |
| 50 | + const output = await pool.run({ port: transferList[0] }, { transferList }) |
| 51 | + expect(output).toBe(`Output of task #${index}`) |
| 52 | + } |
| 53 | + |
| 54 | + port2.off('message', unexpectedTeardown) |
| 55 | + const promise = new Promise((resolve) => port2.on('message', resolve)) |
| 56 | + |
| 57 | + await pool.destroy() |
| 58 | + await expect(promise).resolves.toMatchInlineSnapshot(`"Teardown of task #5"`) |
| 59 | +}) |
0 commit comments