@@ -34,6 +34,9 @@ type fileLoader struct {
34
34
35
35
projectReferenceFileMapper * projectReferenceFileMapper
36
36
dtsDirectories collections.Set [tspath.Path ]
37
+
38
+ pathForLibFileCache collections.SyncMap [string , string ]
39
+ pathForLibFileResolutions collections.SyncMap [tspath.Path , module.ModeAwareCache [* module.ResolvedModule ]]
37
40
}
38
41
39
42
type processedFiles struct {
@@ -59,7 +62,6 @@ type jsxRuntimeImportSpecifier struct {
59
62
60
63
func processAllProgramFiles (
61
64
opts ProgramOptions ,
62
- libs []string ,
63
65
singleThreaded bool ,
64
66
) processedFiles {
65
67
compilerOptions := opts .Config .CompilerOptions ()
@@ -83,11 +85,27 @@ func processAllProgramFiles(
83
85
projectReferenceParseTasks : & fileLoaderWorker [* projectReferenceParseTask ]{
84
86
wg : core .NewWorkGroup (singleThreaded ),
85
87
},
86
- rootTasks : make ([]* parseTask , 0 , len (rootFiles )+ len (libs )),
88
+ rootTasks : make ([]* parseTask , 0 , len (rootFiles )+ len (compilerOptions . Lib )),
87
89
supportedExtensions : core .Flatten (tsoptions .GetSupportedExtensionsWithJsonIfResolveJsonModule (compilerOptions , supportedExtensions )),
88
90
}
89
91
loader .addProjectReferenceTasks ()
90
92
loader .resolver = module .NewResolver (loader .projectReferenceFileMapper .host , compilerOptions , opts .TypingsLocation , opts .ProjectName )
93
+
94
+ var libs []string
95
+ if compilerOptions .NoLib .IsFalseOrUnknown () {
96
+ if compilerOptions .Lib == nil {
97
+ name := tsoptions .GetDefaultLibFileName (compilerOptions )
98
+ libs = append (libs , loader .pathForLibFile (name ))
99
+ } else {
100
+ for _ , lib := range compilerOptions .Lib {
101
+ if name , ok := tsoptions .GetLibFileName (lib ); ok {
102
+ libs = append (libs , loader .pathForLibFile (name ))
103
+ }
104
+ // !!! error on unknown name
105
+ }
106
+ }
107
+ }
108
+
91
109
loader .addRootTasks (rootFiles , false )
92
110
loader .addRootTasks (libs , true )
93
111
loader .addAutomaticTypeDirectiveTasks ()
@@ -105,7 +123,7 @@ func processAllProgramFiles(
105
123
libFiles := make ([]* ast.SourceFile , 0 , totalFileCount ) // totalFileCount here since we append files to it later to construct the final list
106
124
107
125
filesByPath := make (map [tspath.Path ]* ast.SourceFile , totalFileCount )
108
- resolvedModules := make (map [tspath.Path ]module.ModeAwareCache [* module.ResolvedModule ], totalFileCount )
126
+ resolvedModules := make (map [tspath.Path ]module.ModeAwareCache [* module.ResolvedModule ], totalFileCount + 1 )
109
127
typeResolutionsInFile := make (map [tspath.Path ]module.ModeAwareCache [* module.ResolvedTypeReferenceDirective ], totalFileCount )
110
128
sourceFileMetaDatas := make (map [tspath.Path ]ast.SourceFileMetaData , totalFileCount )
111
129
var jsxRuntimeImportSpecifiers map [tspath.Path ]* jsxRuntimeImportSpecifier
@@ -162,6 +180,11 @@ func processAllProgramFiles(
162
180
163
181
allFiles := append (libFiles , files ... )
164
182
183
+ loader .pathForLibFileResolutions .Range (func (key tspath.Path , value module.ModeAwareCache [* module.ResolvedModule ]) bool {
184
+ resolvedModules [key ] = value
185
+ return true
186
+ })
187
+
165
188
return processedFiles {
166
189
resolver : loader .resolver ,
167
190
files : allFiles ,
@@ -463,6 +486,55 @@ func (p *fileLoader) createSyntheticImport(text string, file *ast.SourceFile) *a
463
486
return externalHelpersModuleReference
464
487
}
465
488
489
+ func (p * fileLoader ) pathForLibFile (name string ) string {
490
+ if cached , ok := p .pathForLibFileCache .Load (name ); ok {
491
+ return cached
492
+ }
493
+
494
+ path := tspath .CombinePaths (p .defaultLibraryPath , name )
495
+ if p .opts .Config .CompilerOptions ().LibReplacement .IsTrue () {
496
+ libraryName := getLibraryNameFromLibFileName (name )
497
+ resolveFrom := getInferredLibraryNameResolveFrom (p .opts .Config .CompilerOptions (), p .opts .Host .GetCurrentDirectory (), name )
498
+ resolution := p .resolver .ResolveModuleName (libraryName , resolveFrom , core .ModuleKindCommonJS , nil )
499
+ if resolution .IsResolved () {
500
+ path = resolution .ResolvedFileName
501
+ p .pathForLibFileResolutions .LoadOrStore (p .toPath (resolveFrom ), module.ModeAwareCache [* module.ResolvedModule ]{
502
+ module.ModeAwareCacheKey {Name : libraryName , Mode : core .ModuleKindCommonJS }: resolution ,
503
+ })
504
+ }
505
+ }
506
+
507
+ path , _ = p .pathForLibFileCache .LoadOrStore (name , path )
508
+ return path
509
+ }
510
+
511
+ func getLibraryNameFromLibFileName (libFileName string ) string {
512
+ // Support resolving to lib.dom.d.ts -> @typescript/lib-dom, and
513
+ // lib.dom.iterable.d.ts -> @typescript/lib-dom/iterable
514
+ // lib.es2015.symbol.wellknown.d.ts -> @typescript/lib-es2015/symbol-wellknown
515
+ components := strings .Split (libFileName , "." )
516
+ var path string
517
+ if len (components ) > 1 {
518
+ path = components [1 ]
519
+ }
520
+ i := 2
521
+ for i < len (components ) && components [i ] != "" && components [i ] != "d" {
522
+ path += core .IfElse (i == 2 , "/" , "-" ) + components [i ]
523
+ i ++
524
+ }
525
+ return "@typescript/lib-" + path
526
+ }
527
+
528
+ func getInferredLibraryNameResolveFrom (options * core.CompilerOptions , currentDirectory string , libFileName string ) string {
529
+ var containingDirectory string
530
+ if options .ConfigFilePath != "" {
531
+ containingDirectory = tspath .GetDirectoryPath (options .ConfigFilePath )
532
+ } else {
533
+ containingDirectory = currentDirectory
534
+ }
535
+ return tspath .CombinePaths (containingDirectory , "__lib_node_modules_lookup_" + libFileName + "__.ts" )
536
+ }
537
+
466
538
type resolution struct {
467
539
node * ast.Node
468
540
resolvedModule * module.ResolvedModule
0 commit comments