Skip to content

Commit 2bdfea6

Browse files
committed
loader: Set default 'pretty' option properly
Set the default `options.pretty` value based on stderr rather than stdout, as this is where errors are printed. The loader thread does not get a process.stderr.isTTY set, because its "stderr" is actually a pipe. If `options.pretty` is not set explicitly, the GlobalPreload's `context.port` is used to send a message from the main thread indicating the state of stderr.isTTY. Adds `Service.setPrettyErrors` method to enable setting this value when needed.
1 parent 949d360 commit 2bdfea6

File tree

2 files changed

+33
-6
lines changed

2 files changed

+33
-6
lines changed

src/esm.ts

Lines changed: 22 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ import { extname, resolve as pathResolve } from 'path';
44
import * as assert from 'assert';
55
import { normalizeSlashes, versionGteLt } from './util';
66
import { createRequire } from 'module';
7+
import type { MessagePort } from 'worker_threads';
78

89
// Note: On Windows, URLs look like this: file:///D:/dev/@TypeStrong/ts-node-examples/foo.ts
910

@@ -75,7 +76,7 @@ export namespace NodeLoaderHooksAPI2 {
7576
export interface NodeImportAssertions {
7677
type?: 'json';
7778
}
78-
export type GlobalPreloadHook = () => string;
79+
export type GlobalPreloadHook = (context?: { port: MessagePort }) => string;
7980
}
8081

8182
export type NodeLoaderHooksFormat = 'builtin' | 'commonjs' | 'dynamic' | 'json' | 'module' | 'wasm';
@@ -123,10 +124,29 @@ export function createEsmHooks(tsNodeService: Service) {
123124
globalPreload: useLoaderThread ? globalPreload : undefined,
124125
});
125126

126-
function globalPreload() {
127+
function globalPreload({ port }: { port?: MessagePort } = {}) {
128+
// The loader thread doesn't get process.stderr.isTTY properly,
129+
// so this signal lets us infer it based on the state of the main
130+
// thread, but only relevant if options.pretty is unset.
131+
let stderrTTYSignal: string;
132+
if (tsNodeService.options.pretty === undefined) {
133+
port?.on('message', (data) => {
134+
if (data?.stderrIsTTY) {
135+
tsNodeService.setPrettyErrors(true);
136+
}
137+
});
138+
stderrTTYSignal = `
139+
port.postMessage({
140+
stderrIsTTY: !!process.stderr.isTTY
141+
});
142+
`;
143+
} else {
144+
stderrTTYSignal = '';
145+
}
127146
return `
128147
const { createRequire } = getBuiltin('module');
129148
const require = createRequire(${JSON.stringify(__filename)});
149+
${stderrTTYSignal}
130150
require('./index').register();
131151
`;
132152
}

src/index.ts

Lines changed: 11 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -480,6 +480,7 @@ export interface Service {
480480
ignored(fileName: string): boolean;
481481
compile(code: string, fileName: string, lineOffset?: number): string;
482482
getTypeInfo(code: string, fileName: string, position: number): TypeInfo;
483+
setPrettyErrors(pretty: boolean): void;
483484
/** @internal */
484485
configFilePath: string | undefined;
485486
/** @internal */
@@ -719,11 +720,16 @@ export function createFromPreloadedConfig(foundConfigResult: ReturnType<typeof f
719720
});
720721
}
721722

722-
const shouldHavePrettyErrors = options.pretty === undefined ? process.stdout.isTTY : options.pretty;
723+
let shouldHavePrettyErrors!: boolean;
724+
let formatDiagnostics: (diagnostics: readonly _ts.Diagnostic[], host: _ts.FormatDiagnosticsHost) => string;
723725

724-
const formatDiagnostics = shouldHavePrettyErrors
725-
? ts.formatDiagnosticsWithColorAndContext || ts.formatDiagnostics
726-
: ts.formatDiagnostics;
726+
function setPrettyErrors(pretty: boolean) {
727+
shouldHavePrettyErrors = pretty;
728+
formatDiagnostics = shouldHavePrettyErrors
729+
? ts.formatDiagnosticsWithColorAndContext || ts.formatDiagnostics
730+
: ts.formatDiagnostics;
731+
}
732+
setPrettyErrors(options.pretty !== undefined ? options.pretty : !!process.stderr.isTTY);
727733

728734
function createTSError(diagnostics: ReadonlyArray<_ts.Diagnostic>) {
729735
const diagnosticText = formatDiagnostics(diagnostics, diagnosticHost);
@@ -1282,6 +1288,7 @@ export function createFromPreloadedConfig(foundConfigResult: ReturnType<typeof f
12821288
getNodeEsmGetFormat,
12831289
getNodeCjsLoader,
12841290
extensions,
1291+
setPrettyErrors,
12851292
};
12861293
}
12871294

0 commit comments

Comments
 (0)