-
Notifications
You must be signed in to change notification settings - Fork 13.1k
Description
π Search Terms
watchOptions, working directory, cwd, tsconfig, excludeDirectories, excludeFiles
π Version & Regression Information
- This is the behavior in every version I tried, and I reviewed the FAQ for entries about watchOptions
β― Playground Link
No response
π» Code
const path = require('node:path');
const ts = require('typescript');
const tsConfigPath = // Some path to a valid tsconfig with watch options defined.
const parsedConfigFile = ts.readConfigFile(tsConfigPath, sys.readFile);
const basePath = path.dirname(tsConfigPath);
const sys = {
...ts.sys,
getCurrentDirectory: () => basePath // ts.sys.getCurrentDirectory() returns the memoized value of process.cwd() as of when `require('typescript')` executed
};
const tsconfig = ts.parseJsonConfigFileContent(
parsedConfigFile.config,
{
fileExists: sys.fileExists,
readFile: sys.readFile,
readDirectory: sys.readDirectory,
useCaseSensitiveFileNames: true
},
basePath,
/*existingOptions:*/ undefined,
tsConfigPath
);
const compilerHost = ts.createWatchCompilerHost(tsconfig.fileNames, tsconfig.options, sys, undefined, undefined, undefined, tsconfig.projectReferences, tsconfig.watchOptions);
const watchProgram = ts.createWatchProgram(compilerHost);π Actual behavior
Typescript evaluates watchOptions.excludeFiles and watchOptions.excludeDirectories relative to the value of process.cwd() as of the moment the require('typescript') call evaluated.
Edit: the value gets memoized upon the first invocation of ts.sys.getCurrentDirectory() (which is captured via closure and therefore not overrideable).
π Expected behavior
The watchOptions.excludeFiles and watchOptions.excludeDirectories patterns are evaluated relative to the folder containing the tsconfig file.
Additional information about the issue
The expressions here evaluate excludeFiles and excludeDirectories using a value of basePath that is a memoized invocation of process.cwd() at the moment ts.sys was created:
TypeScript/src/compiler/sys.ts
Lines 866 to 869 in 6cc605f
| return (options?.excludeDirectories || options?.excludeFiles) && ( | |
| matchesExclude(pathToCheck, options?.excludeFiles, useCaseSensitiveFileNames, getCurrentDirectory()) || | |
| matchesExclude(pathToCheck, options?.excludeDirectories, useCaseSensitiveFileNames, getCurrentDirectory()) | |
| ); |
This interferes with the ability to run multiple instances of the TypeScript compiler in watch mode in the same process concurrently, or even to run the compiler in watch mode via the API in a root folder other than the current process working directory (and changing the current working directory doesn't work either).