diff --git a/packages/cli/src/lib/builder/buildTypeDefinitions.ts b/packages/cli/src/lib/builder/buildTypeDefinitions.ts index 85e54850e4..3bf3a4495f 100644 --- a/packages/cli/src/lib/builder/buildTypeDefinitions.ts +++ b/packages/cli/src/lib/builder/buildTypeDefinitions.ts @@ -16,10 +16,10 @@ import fs from 'fs-extra'; import chalk from 'chalk'; -import { Worker } from 'worker_threads'; import { relative as relativePath, resolve as resolvePath } from 'path'; import { paths } from '../paths'; import { buildTypeDefinitionsWorker } from './buildTypeDefinitionsWorker'; +import { runWorkerThreads } from '../parallel'; // These message types are ignored since we want to avoid duplicating the logic of // handling them correctly, and we already have the API Reports warning about them. @@ -84,59 +84,46 @@ export async function buildTypeDefinitions( const typescriptDir = paths.resolveTargetRoot('node_modules/typescript'); const hasTypescript = await fs.pathExists(typescriptDir); const typescriptCompilerFolder = hasTypescript ? typescriptDir : undefined; - - const worker = new Worker(`(${buildTypeDefinitionsWorker})()`, { - eval: true, + await runWorkerThreads({ + threadCount: 1, workerData: { entryPoints, workerConfigs, typescriptCompilerFolder, }, - }); - - await new Promise((resolve, reject) => { - worker.once('error', reject); - worker.once('exit', code => { - if (code) { - reject(new Error(`Worker exited with code ${code}`)); + worker: buildTypeDefinitionsWorker, + onMessage: ({ + message, + targetTypesDir, + }: { + message: any; + targetTypesDir: string; + }) => { + if (ignoredMessages.has(message.messageId)) { + return; } - }); - worker.on('message', data => { - if (data.type === 'done') { - if (data.error) { - reject(data.error); - } else { - resolve(); - } - } else if (data.type === 'message') { - const { message, targetTypesDir } = data; - if (ignoredMessages.has(message.messageId)) { - return; - } - - let text = `${message.text} (${message.messageId})`; - if (message.sourceFilePath) { - text += ' at '; - text += relativePath(targetTypesDir, message.sourceFilePath); - if (message.sourceFileLine) { - text += `:${message.sourceFileLine}`; - if (message.sourceFileColumn) { - text += `:${message.sourceFileColumn}`; - } + let text = `${message.text} (${message.messageId})`; + if (message.sourceFilePath) { + text += ' at '; + text += relativePath(targetTypesDir, message.sourceFilePath); + if (message.sourceFileLine) { + text += `:${message.sourceFileLine}`; + if (message.sourceFileColumn) { + text += `:${message.sourceFileColumn}`; } } - if (message.logLevel === 'error') { - console.error(chalk.red(`Error: ${text}`)); - } else if ( - message.logLevel === 'warning' || - message.category === 'Extractor' - ) { - console.warn(`Warning: ${text}`); - } else { - console.log(text); - } } - }); + if (message.logLevel === 'error') { + console.error(chalk.red(`Error: ${text}`)); + } else if ( + message.logLevel === 'warning' || + message.category === 'Extractor' + ) { + console.warn(`Warning: ${text}`); + } else { + console.log(text); + } + }, }); } diff --git a/packages/cli/src/lib/builder/buildTypeDefinitionsWorker.ts b/packages/cli/src/lib/builder/buildTypeDefinitionsWorker.ts index 8cb843f58e..43e5cbc526 100644 --- a/packages/cli/src/lib/builder/buildTypeDefinitionsWorker.ts +++ b/packages/cli/src/lib/builder/buildTypeDefinitionsWorker.ts @@ -20,7 +20,10 @@ * be self-contained. * Using TypeScript is fine as it is transpiled before being stringified. */ -export function buildTypeDefinitionsWorker() { +export async function buildTypeDefinitionsWorker( + workerData: any, + sendMessage: (message: any) => void, +) { try { require('@microsoft/api-extractor'); } catch (error) { @@ -31,7 +34,6 @@ export function buildTypeDefinitionsWorker() { } const { dirname } = require('path'); - const { workerData, parentPort } = require('worker_threads'); const { entryPoints, workerConfigs, typescriptCompilerFolder } = workerData; const apiExtractor = require('@microsoft/api-extractor'); @@ -63,7 +65,6 @@ export function buildTypeDefinitionsWorker() { return old.call(this, path); }; - let success = true; let compilerState; for (const { extractorOptions, targetTypesDir } of workerConfigs) { const extractorConfig = ExtractorConfig.prepare(extractorOptions); @@ -82,24 +83,15 @@ export function buildTypeDefinitionsWorker() { showDiagnostics: false, messageCallback: (message: any) => { message.handled = true; - parentPort.postMessage({ type: 'message', message, targetTypesDir }); + sendMessage({ message, targetTypesDir }); }, }); if (!extractorResult.succeeded) { - parentPort.postMessage({ - type: 'done', - error: new Error( - `Type definition build completed with ${extractorResult.errorCount} errors` + - ` and ${extractorResult.warningCount} warnings`, - ), - }); - success = false; - break; + throw new Error( + `Type definition build completed with ${extractorResult.errorCount} errors` + + ` and ${extractorResult.warningCount} warnings`, + ); } } - - if (success) { - parentPort.postMessage({ type: 'done' }); - } }