diff --git a/packages/jest-worker/src/workers/__tests__/threadChild.test.ts b/packages/jest-worker/src/workers/__tests__/threadChild.test.ts index 649317919f6f..b7637963969f 100644 --- a/packages/jest-worker/src/workers/__tests__/threadChild.test.ts +++ b/packages/jest-worker/src/workers/__tests__/threadChild.test.ts @@ -365,3 +365,24 @@ it('throws if child is not forked', () => { messagePort.emit('message', [CHILD_MESSAGE_CALL, true, 'fooThrows', []]); }).toThrow('_worker_threads.parentPort.postMessage is not a function'); }); + +it('handle error if `postMessage` throws an error', () => { + messagePort.emit('message', [ + CHILD_MESSAGE_INITIALIZE, + true, + './my-fancy-worker', + ]); + + jest.mocked(messagePort.postMessage).mockImplementationOnce(() => { + throw mockError; + }); + + messagePort.emit('message', [CHILD_MESSAGE_CALL, true, 'fooWorks', []]); + expect(jest.mocked(messagePort.postMessage).mock.calls[1][0]).toEqual([ + PARENT_MESSAGE_CLIENT_ERROR, + 'TypeError', + 'Boo', + mockError.stack, + {}, + ]); +}); diff --git a/packages/jest-worker/src/workers/threadChild.ts b/packages/jest-worker/src/workers/threadChild.ts index 2380e1afd23c..efd31d04ed37 100644 --- a/packages/jest-worker/src/workers/threadChild.ts +++ b/packages/jest-worker/src/workers/threadChild.ts @@ -112,7 +112,14 @@ function reportSuccess(result: unknown) { throw new Error('Child can only be used on a forked process'); } - parentPort!.postMessage([PARENT_MESSAGE_OK, result]); + try { + parentPort!.postMessage([PARENT_MESSAGE_OK, result]); + } catch (err: any) { + // Handling it here to avoid unhandled `DataCloneError` rejection + // which is hard to distinguish on the parent side + // (such error doesn't have any message or stack trace) + reportClientError(err); + } } function reportClientError(error: Error) {