diff --git a/packages/eslint-plugin/tests/rules/non-nullable-type-assertion-style.test.ts b/packages/eslint-plugin/tests/rules/non-nullable-type-assertion-style.test.ts index 4b0750c8c84..365de88c36a 100644 --- a/packages/eslint-plugin/tests/rules/non-nullable-type-assertion-style.test.ts +++ b/packages/eslint-plugin/tests/rules/non-nullable-type-assertion-style.test.ts @@ -1,14 +1,11 @@ -import path from 'path'; - import rule from '../../src/rules/non-nullable-type-assertion-style'; -import { RuleTester } from '../RuleTester'; +import { getFixturesRootDir, RuleTester } from '../RuleTester'; -const rootDir = path.resolve(__dirname, '../fixtures/'); const ruleTester = new RuleTester({ parserOptions: { sourceType: 'module', - tsconfigRootDir: rootDir, - project: './tsconfig.noUncheckedIndexedAccess.json', + tsconfigRootDir: getFixturesRootDir(), + project: './tsconfig.json', }, parser: '@typescript-eslint/parser', }); @@ -62,35 +59,6 @@ const x = 1 as 1; declare function foo(): T; const bar = foo() as number; `, - ` -function first(array: ArrayLike): T | null { - return array.length > 0 ? (array[0] as T) : null; -} - `, - ` -function first(array: ArrayLike): T | null { - return array.length > 0 ? (array[0] as T) : null; -} - `, - ` -function first(array: ArrayLike): T | null { - return array.length > 0 ? (array[0] as T) : null; -} - `, - ` -function first( - array: ArrayLike, -): T | null { - return array.length > 0 ? (array[0] as T) : null; -} - `, - ` -type A = 'a' | 'A'; -type B = 'b' | 'B'; -function first(array: ArrayLike): T | null { - return array.length > 0 ? (array[0] as T) : null; -} - `, ], invalid: [ @@ -229,24 +197,73 @@ declare const x: T; const y = x!; `, }, - { - code: ` -function first(array: ArrayLike): T | null { + ], +}); + +const ruleTesterWithNoUncheckedIndexAccess = new RuleTester({ + parserOptions: { + sourceType: 'module', + tsconfigRootDir: getFixturesRootDir(), + project: './tsconfig.noUncheckedIndexedAccess.json', + }, + parser: '@typescript-eslint/parser', +}); + +ruleTesterWithNoUncheckedIndexAccess.run( + 'non-nullable-type-assertion-style - noUncheckedIndexedAccess', + rule, + { + valid: [ + ` +function first(array: ArrayLike): T | null { return array.length > 0 ? (array[0] as T) : null; } `, - errors: [ - { - column: 30, - line: 3, - messageId: 'preferNonNullAssertion', - }, - ], - output: ` + ` +function first(array: ArrayLike): T | null { + return array.length > 0 ? (array[0] as T) : null; +} + `, + ` +function first(array: ArrayLike): T | null { + return array.length > 0 ? (array[0] as T) : null; +} + `, + ` +function first( + array: ArrayLike, +): T | null { + return array.length > 0 ? (array[0] as T) : null; +} + `, + ` +type A = 'a' | 'A'; +type B = 'b' | 'B'; +function first(array: ArrayLike): T | null { + return array.length > 0 ? (array[0] as T) : null; +} + `, + ], + invalid: [ + { + code: ` +function first(array: ArrayLike): T | null { + return array.length > 0 ? (array[0] as T) : null; +} + `, + errors: [ + { + column: 30, + line: 3, + messageId: 'preferNonNullAssertion', + }, + ], + output: ` function first(array: ArrayLike): T | null { return array.length > 0 ? (array[0]!) : null; } - `, - }, - ], -}); + `, + }, + ], + }, +); diff --git a/packages/typescript-estree/src/create-program/createWatchProgram.ts b/packages/typescript-estree/src/create-program/createWatchProgram.ts index 0e32f8ec1e5..d17835fff3c 100644 --- a/packages/typescript-estree/src/create-program/createWatchProgram.ts +++ b/packages/typescript-estree/src/create-program/createWatchProgram.ts @@ -159,11 +159,21 @@ function getProgramsForProjects(parseSettings: ParseSettings): ts.Program[] { ); } + const currentProjectsFromSettings = new Set(parseSettings.projects); + /* * before we go into the process of attempting to find and update every program * see if we know of a program that contains this file */ for (const [tsconfigPath, existingWatch] of knownWatchProgramMap.entries()) { + if (!currentProjectsFromSettings.has(tsconfigPath)) { + // the current parser run doesn't specify this tsconfig in parserOptions.project + // so we don't want to consider it for caching purposes. + // + // if we did consider it we might return a program for a project + // that wasn't specified in the current parser run (which is obv bad!). + continue; + } let fileList = programFileListCache.get(tsconfigPath); let updatedProgram: ts.Program | null = null; if (!fileList) {