7
7
arrayToMap ,
8
8
BuilderState ,
9
9
CachedDirectoryStructureHost ,
10
+ changeExtension ,
10
11
changesAffectModuleResolution ,
11
12
clearMap ,
12
13
cloneCompilerOptions ,
@@ -16,7 +17,6 @@ import {
16
17
comparePaths ,
17
18
CompilerHost ,
18
19
CompilerOptions ,
19
- concatenate ,
20
20
containsPath ,
21
21
createCacheableExportInfoMap ,
22
22
createLanguageService ,
@@ -50,6 +50,7 @@ import {
50
50
getAutomaticTypeDirectiveNames ,
51
51
getBaseFileName ,
52
52
GetCanonicalFileName ,
53
+ getCommonSourceDirectoryOfConfig ,
53
54
getDeclarationEmitOutputFilePathWorker ,
54
55
getDefaultCompilerOptions ,
55
56
getDefaultLibFileName ,
@@ -60,6 +61,7 @@ import {
60
61
getEntrypointsFromPackageJsonInfo ,
61
62
getNormalizedAbsolutePath ,
62
63
getOrUpdate ,
64
+ getOutputDeclarationFileName ,
63
65
GetPackageJsonEntrypointsHost ,
64
66
getStringComparer ,
65
67
HasInvalidatedLibResolutions ,
@@ -79,6 +81,7 @@ import {
79
81
map ,
80
82
mapDefined ,
81
83
maybeBind ,
84
+ memoize ,
82
85
ModuleResolutionCache ,
83
86
ModuleResolutionHost ,
84
87
noop ,
@@ -1316,6 +1319,12 @@ export abstract class Project implements LanguageServiceHost, ModuleResolutionHo
1316
1319
}
1317
1320
}
1318
1321
1322
+ /** @internal */
1323
+ markAutoImportProviderAsDirty ( ) {
1324
+ if ( ! this . autoImportProviderHost ) this . autoImportProviderHost = undefined ;
1325
+ this . autoImportProviderHost ?. markAsDirty ( ) ;
1326
+ }
1327
+
1319
1328
/** @internal */
1320
1329
onAutoImportProviderSettingsChanged ( ) {
1321
1330
if ( this . autoImportProviderHost === false ) {
@@ -1400,8 +1409,7 @@ export abstract class Project implements LanguageServiceHost, ModuleResolutionHo
1400
1409
this . projectProgramVersion ++ ;
1401
1410
}
1402
1411
if ( hasAddedorRemovedFiles ) {
1403
- if ( ! this . autoImportProviderHost ) this . autoImportProviderHost = undefined ;
1404
- this . autoImportProviderHost ?. markAsDirty ( ) ;
1412
+ this . markAutoImportProviderAsDirty ( ) ;
1405
1413
}
1406
1414
if ( isFirstProgramLoad ) {
1407
1415
// Preload auto import provider so it's not created during completions request
@@ -2439,7 +2447,7 @@ export class AutoImportProviderProject extends Project {
2439
2447
2440
2448
const start = timestamp ( ) ;
2441
2449
let dependencyNames : Set < string > | undefined ;
2442
- let rootNames : string [ ] | undefined ;
2450
+ let rootNames : Set < string > | undefined ;
2443
2451
const rootFileName = combinePaths ( hostProject . currentDirectory , inferredTypesContainingFile ) ;
2444
2452
const packageJsons = hostProject . getPackageJsonsForAutoImport ( combinePaths ( hostProject . currentDirectory , rootFileName ) ) ;
2445
2453
for ( const packageJson of packageJsons ) {
@@ -2471,8 +2479,7 @@ export class AutoImportProviderProject extends Project {
2471
2479
if ( packageJson ) {
2472
2480
const entrypoints = getRootNamesFromPackageJson ( packageJson , program , symlinkCache ) ;
2473
2481
if ( entrypoints ) {
2474
- rootNames = concatenate ( rootNames , entrypoints ) ;
2475
- dependenciesAdded += entrypoints . length ? 1 : 0 ;
2482
+ dependenciesAdded += addRootNames ( entrypoints ) ;
2476
2483
continue ;
2477
2484
}
2478
2485
}
@@ -2490,8 +2497,7 @@ export class AutoImportProviderProject extends Project {
2490
2497
) ;
2491
2498
if ( typesPackageJson ) {
2492
2499
const entrypoints = getRootNamesFromPackageJson ( typesPackageJson , program , symlinkCache ) ;
2493
- rootNames = concatenate ( rootNames , entrypoints ) ;
2494
- dependenciesAdded += entrypoints ?. length ? 1 : 0 ;
2500
+ dependenciesAdded += addRootNames ( entrypoints ) ;
2495
2501
return true ;
2496
2502
}
2497
2503
}
@@ -2504,16 +2510,56 @@ export class AutoImportProviderProject extends Project {
2504
2510
// package and load the JS.
2505
2511
if ( packageJson && compilerOptions . allowJs && compilerOptions . maxNodeModuleJsDepth ) {
2506
2512
const entrypoints = getRootNamesFromPackageJson ( packageJson , program , symlinkCache , /*resolveJs*/ true ) ;
2507
- rootNames = concatenate ( rootNames , entrypoints ) ;
2508
- dependenciesAdded += entrypoints ?. length ? 1 : 0 ;
2513
+ dependenciesAdded += addRootNames ( entrypoints ) ;
2509
2514
}
2510
2515
}
2511
2516
}
2512
2517
2513
- if ( rootNames ?. length ) {
2514
- hostProject . log ( `AutoImportProviderProject: found ${ rootNames . length } root files in ${ dependenciesAdded } dependencies in ${ timestamp ( ) - start } ms` ) ;
2518
+ const references = program . getResolvedProjectReferences ( ) ;
2519
+ let referencesAddded = 0 ;
2520
+ if ( references ?. length && hostProject . projectService . getHostPreferences ( ) . includeCompletionsForModuleExports ) {
2521
+ // Add direct referenced projects to rootFiles names
2522
+ references . forEach ( ref => {
2523
+ if ( ref ?. commandLine . options . outFile ) {
2524
+ referencesAddded += addRootNames ( filterEntrypoints ( [
2525
+ changeExtension ( ref . commandLine . options . outFile , ".d.ts" ) ,
2526
+ ] ) ) ;
2527
+ }
2528
+ else if ( ref ) {
2529
+ const getCommonSourceDirectory = memoize ( ( ) =>
2530
+ getCommonSourceDirectoryOfConfig (
2531
+ ref . commandLine ,
2532
+ ! hostProject . useCaseSensitiveFileNames ( ) ,
2533
+ )
2534
+ ) ;
2535
+ referencesAddded += addRootNames ( filterEntrypoints ( mapDefined (
2536
+ ref . commandLine . fileNames ,
2537
+ fileName =>
2538
+ ! isDeclarationFileName ( fileName ) &&
2539
+ ! fileExtensionIs ( fileName , Extension . Json ) &&
2540
+ ! program . getSourceFile ( fileName ) ?
2541
+ getOutputDeclarationFileName (
2542
+ fileName ,
2543
+ ref . commandLine ,
2544
+ ! hostProject . useCaseSensitiveFileNames ( ) ,
2545
+ getCommonSourceDirectory ,
2546
+ ) : undefined ,
2547
+ ) ) ) ;
2548
+ }
2549
+ } ) ;
2550
+ }
2551
+
2552
+ if ( rootNames ?. size ) {
2553
+ hostProject . log ( `AutoImportProviderProject: found ${ rootNames . size } root files in ${ dependenciesAdded } dependencies ${ referencesAddded } referenced projects in ${ timestamp ( ) - start } ms` ) ;
2554
+ }
2555
+ return rootNames ? arrayFrom ( rootNames . values ( ) ) : ts . emptyArray ;
2556
+
2557
+ function addRootNames ( entrypoints : readonly string [ ] | undefined ) {
2558
+ if ( ! entrypoints ?. length ) return 0 ;
2559
+ rootNames ??= new Set ( ) ;
2560
+ entrypoints . forEach ( entry => rootNames ! . add ( entry ) ) ;
2561
+ return 1 ;
2515
2562
}
2516
- return rootNames || ts . emptyArray ;
2517
2563
2518
2564
function addDependency ( dependency : string ) {
2519
2565
if ( ! startsWith ( dependency , "@types/" ) ) {
@@ -2540,14 +2586,18 @@ export class AutoImportProviderProject extends Project {
2540
2586
} ) ;
2541
2587
}
2542
2588
2543
- return mapDefined ( entrypoints , entrypoint => {
2544
- const resolvedFileName = isSymlink ? entrypoint . replace ( packageJson . packageDirectory , real ! ) : entrypoint ;
2545
- if ( ! program . getSourceFile ( resolvedFileName ) && ! ( isSymlink && program . getSourceFile ( entrypoint ) ) ) {
2546
- return resolvedFileName ;
2547
- }
2548
- } ) ;
2589
+ return filterEntrypoints ( entrypoints , isSymlink ? entrypoint => entrypoint . replace ( packageJson . packageDirectory , real ! ) : undefined ) ;
2549
2590
}
2550
2591
}
2592
+
2593
+ function filterEntrypoints ( entrypoints : readonly string [ ] | undefined , symlinkName ?: ( entrypoint : string ) => string ) {
2594
+ return mapDefined ( entrypoints , entrypoint => {
2595
+ const resolvedFileName = symlinkName ? symlinkName ( entrypoint ) : entrypoint ;
2596
+ if ( ! program ! . getSourceFile ( resolvedFileName ) && ! ( symlinkName && program ! . getSourceFile ( entrypoint ) ) ) {
2597
+ return resolvedFileName ;
2598
+ }
2599
+ } ) ;
2600
+ }
2551
2601
}
2552
2602
2553
2603
/** @internal */
0 commit comments