forked from TypeStrong/ts-node
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Fix ESM node processes being unable to fork into other scripts
Currently, Node processes instantiated through the `--esm` flag result in a child process being created so that the ESM loader can be registered. This works fine and is reasonable. The child process approach to register ESM hooks currently prevents the NodeJS `fork` method from being used because the `execArgv` propagated into forked processes causes `ts-node` (which is also propagated as child exec script -- this is good because it allows nested type resolution to work) to always execute the original entry-point, causing potential infinite loops because the designated fork module script is not executed as expected. This commit fixes this by not encoding the entry-point information into the state that is captured as part of the `execArgv`. Instead the entry-point information is always retrieved from the parsed rest command line arguments in the final stage (`phase4`). Additionally, this PR streamlines the boostrap mechanism to always call into the child script, resulting in reduced complexity, and also improved caching for user-initiated forked processes. i.e. the tsconfig resolution is not repeated multiple-times because forked processes are expected to preserve the existing ts-node project. More details can be found here TypeStrong#1831. Fixes TypeStrong#1812.
- Loading branch information
1 parent
3333005
commit 4c3390a
Showing
33 changed files
with
390 additions
and
204 deletions.
There are no files selected for viewing
Large diffs are not rendered by default.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,24 +1,11 @@ | ||
import { BootstrapState, bootstrap } from '../bin'; | ||
import { completeBootstrap, BootstrapStateForChild } from '../bin'; | ||
import { argPrefix, compress, decompress } from './argv-payload'; | ||
|
||
const base64ConfigArg = process.argv[2]; | ||
if (!base64ConfigArg.startsWith(argPrefix)) throw new Error('unexpected argv'); | ||
const base64Payload = base64ConfigArg.slice(argPrefix.length); | ||
const state = decompress(base64Payload) as BootstrapState; | ||
const state = decompress(base64Payload) as BootstrapStateForChild; | ||
|
||
state.isInChildProcess = true; | ||
state.tsNodeScript = __filename; | ||
state.parseArgvResult.argv = process.argv; | ||
state.parseArgvResult.restArgs = process.argv.slice(3); | ||
|
||
// Modify and re-compress the payload delivered to subsequent child processes. | ||
// This logic may be refactored into bin.ts by https://github.com/TypeStrong/ts-node/issues/1831 | ||
if (state.isCli) { | ||
const stateForChildren: BootstrapState = { | ||
...state, | ||
isCli: false, | ||
}; | ||
state.parseArgvResult.argv[2] = `${argPrefix}${compress(stateForChildren)}`; | ||
} | ||
|
||
bootstrap(state); | ||
completeBootstrap(state); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
import { pathToFileURL } from 'url'; | ||
import { brotliCompressSync } from 'zlib'; | ||
import type { BootstrapStateForChild } from '../bin'; | ||
import { versionGteLt } from '../util'; | ||
|
||
const argPrefix = '--brotli-base64-config='; | ||
|
||
export function getChildProcessArguments( | ||
enableEsmLoader: boolean, | ||
state: BootstrapStateForChild | ||
) { | ||
if (enableEsmLoader && !versionGteLt(process.versions.node, '12.17.0')) { | ||
throw new Error( | ||
'`ts-node-esm` and `ts-node --esm` require node version 12.17.0 or newer.' | ||
); | ||
} | ||
|
||
const nodeExecArgs = []; | ||
|
||
if (enableEsmLoader) { | ||
nodeExecArgs.push( | ||
'--require', | ||
require.resolve('./child-require.js'), | ||
'--loader', | ||
// Node on Windows doesn't like `c:\` absolute paths here; must be `file:///c:/` | ||
pathToFileURL(require.resolve('../../child-loader.mjs')).toString() | ||
); | ||
} | ||
|
||
const childScriptArgs = [ | ||
`${argPrefix}${brotliCompressSync( | ||
Buffer.from(JSON.stringify(state), 'utf8') | ||
).toString('base64')}`, | ||
]; | ||
|
||
return { | ||
nodeExecArgs, | ||
childScriptArgs, | ||
childScriptPath: require.resolve('./child-entrypoint.js'), | ||
}; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
4 changes: 0 additions & 4 deletions
4
...child-process/process-forking-js/index.ts → ...rocess/process-forking-js-worker/index.ts
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
File renamed without changes.
3 changes: 0 additions & 3 deletions
3
...cess/process-forking-ts-abs/tsconfig.json → ...s/process-forking-js-worker/tsconfig.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,8 +1,5 @@ | ||
{ | ||
"compilerOptions": { | ||
"module": "ESNext" | ||
}, | ||
"ts-node": { | ||
"swc": true | ||
} | ||
} |
File renamed without changes.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
8 changes: 8 additions & 0 deletions
8
tests/esm-child-process/process-forking-nested-esm-node-next/tsconfig.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
{ | ||
"compilerOptions": { | ||
"module": "NodeNext" | ||
}, | ||
"ts-node": { | ||
"transpileOnly": true | ||
} | ||
} |
File renamed without changes.
Oops, something went wrong.