Skip to content

Commit d7cfc01

Browse files
committed
Explain if file is imported using "@typescript/lib"
1 parent c54cfef commit d7cfc01

14 files changed

+128
-88
lines changed

src/compiler/diagnosticMessages.json

+8
Original file line numberDiff line numberDiff line change
@@ -1524,6 +1524,14 @@
15241524
"category": "Message",
15251525
"code": 1461
15261526
},
1527+
"Library '{0}' specified in compilerOptions and imported via '{1}'": {
1528+
"category": "Message",
1529+
"code": 1462
1530+
},
1531+
"Library referenced via '{0}' from file '{1}' and imported via '{2}'": {
1532+
"category": "Message",
1533+
"code": 1463
1534+
},
15271535

15281536
"The 'import.meta' meta-property is not allowed in files which will build into CommonJS output.": {
15291537
"category": "Error",

src/compiler/program.ts

+31-29
Original file line numberDiff line numberDiff line change
@@ -1052,12 +1052,6 @@ export function loadWithModeAwareCache<Entry, SourceFile, ResolutionCache, Resol
10521052
return resolutions;
10531053
}
10541054

1055-
function getLibFileName(libReference: FileReference) {
1056-
const libName = toFileNameLowerCase(libReference.fileName);
1057-
const libFileName = libMap.get(libName);
1058-
return { libName, libFileName };
1059-
}
1060-
10611055
/** @internal */
10621056
export function forEachResolvedProjectReference<T>(
10631057
resolvedProjectReferences: readonly (ResolvedProjectReference | undefined)[] | undefined,
@@ -1107,11 +1101,33 @@ function forEachProjectReference<T>(
11071101
export const inferredTypesContainingFile = "__inferred type names__.ts";
11081102

11091103
/** @internal */
1110-
export function getInferredLibrarayNameResolveFrom(options: CompilerOptions, currentDirectory: string, libFileName: string) {
1104+
export function getInferredLibraryNameResolveFrom(options: CompilerOptions, currentDirectory: string, libFileName: string) {
11111105
const containingDirectory = options.configFilePath ? getDirectoryPath(options.configFilePath) : currentDirectory;
11121106
return combinePaths(containingDirectory, `__lib_node_modules_lookup_${libFileName}__.ts`);
11131107
}
11141108

1109+
/** @internal */
1110+
export function getLibraryNameFromLibFileName(libFileName: string) {
1111+
// Support resolving to lib.dom.d.ts -> @typescript/lib-dom, and
1112+
// lib.dom.iterable.d.ts -> @typescript/lib-dom/iterable
1113+
// lib.es2015.symbol.wellknown.d.ts -> @typescript/lib-es2015/symbol-wellknown
1114+
const components = libFileName.split(".");
1115+
let path = components[1];
1116+
let i = 2;
1117+
while (components[i] && components[i] !== "d") {
1118+
path += (i === 2 ? "/" : "-") + components[i];
1119+
i++;
1120+
}
1121+
return "@typescript/lib-" + path;
1122+
}
1123+
1124+
/** @internal */
1125+
export function getLibFileNameFromLibReference(libReference: FileReference) {
1126+
const libName = toFileNameLowerCase(libReference.fileName);
1127+
const libFileName = libMap.get(libName);
1128+
return { libName, libFileName };
1129+
}
1130+
11151131
interface DiagnosticCache<T extends Diagnostic> {
11161132
perFile?: Map<Path, readonly T[]>;
11171133
allDiagnostics?: readonly T[];
@@ -1229,7 +1245,7 @@ export function isProgramUptoDate(
12291245
return !sourceFileVersionUptoDate(sourceFile) ||
12301246
hasInvalidatedResolutions(sourceFile.path) ||
12311247
some(sourceFile.libReferenceDirectives, libRef => {
1232-
const { libFileName } = getLibFileName(libRef);
1248+
const { libFileName } = getLibFileNameFromLibReference(libRef);
12331249
return !!libFileName && hasInvalidatedLibResolutions(libFileName);
12341250
});
12351251
}
@@ -2472,7 +2488,7 @@ export function createProgram(rootNamesOrOptions: readonly string[] | CreateProg
24722488
// Do this resolution if necessary to determine reconstruction of program
24732489
if (structureIsReused !== StructureIsReused.Completely &&
24742490
some(newSourceFile.libReferenceDirectives, libReference => {
2475-
const { libFileName } = getLibFileName(libReference);
2491+
const { libFileName } = getLibFileNameFromLibReference(libReference);
24762492
return !!libFileName &&
24772493
pathForLibFileWorker(libFileName).actual !== oldProgram?.resolvedLibReferences?.get(libFileName)?.actual;
24782494
})) {
@@ -3362,7 +3378,7 @@ export function createProgram(rootNamesOrOptions: readonly string[] | CreateProg
33623378
}
33633379

33643380
function getLibFileFromReference(ref: FileReference) {
3365-
const { libFileName } = getLibFileName(ref);
3381+
const { libFileName } = getLibFileNameFromLibReference(ref);
33663382
const actualFileName = libFileName && resolvedLibReferences?.get(libFileName)?.actual;
33673383
return actualFileName !== undefined ? getSourceFile(actualFileName) : undefined;
33683384
}
@@ -3867,20 +3883,6 @@ export function createProgram(rootNamesOrOptions: readonly string[] | CreateProg
38673883
return result.actual;
38683884
}
38693885

3870-
function getLibraryName(libFileName: string) {
3871-
// Support resolving to lib.dom.d.ts -> @typescript/lib-dom, and
3872-
// lib.dom.iterable.d.ts -> @typescript/lib-dom/iterable
3873-
// lib.es2015.symbol.wellknown.d.ts -> @typescript/lib-es2015/symbol-wellknown
3874-
const components = libFileName.split(".");
3875-
let path = components[1];
3876-
let i = 2;
3877-
while (components[i] && components[i] !== "d") {
3878-
path += (i === 2 ? "/" : "-") + components[i];
3879-
i++;
3880-
}
3881-
return "@typescript/lib-" + path;
3882-
}
3883-
38843886
function pathForLibFileWorker(libFileName: string): LibResolution {
38853887
const existing = resolvedLibProcessing?.get(libFileName);
38863888
if (existing) return existing;
@@ -3889,8 +3891,8 @@ export function createProgram(rootNamesOrOptions: readonly string[] | CreateProg
38893891
const oldResolution = oldProgram.resolvedLibReferences?.get(libFileName);
38903892
if (oldResolution) {
38913893
if (oldResolution.resolution && isTraceEnabled(options, host)) {
3892-
const libraryName = getLibraryName(libFileName);
3893-
const resolveFrom = getInferredLibrarayNameResolveFrom(options, currentDirectory, libFileName);
3894+
const libraryName = getLibraryNameFromLibFileName(libFileName);
3895+
const resolveFrom = getInferredLibraryNameResolveFrom(options, currentDirectory, libFileName);
38943896
trace(host,
38953897
oldResolution.resolution.resolvedModule ?
38963898
oldResolution.resolution.resolvedModule.packageId ?
@@ -3908,8 +3910,8 @@ export function createProgram(rootNamesOrOptions: readonly string[] | CreateProg
39083910
}
39093911
}
39103912

3911-
const libraryName = getLibraryName(libFileName);
3912-
const resolveFrom = getInferredLibrarayNameResolveFrom(options, currentDirectory, libFileName);
3913+
const libraryName = getLibraryNameFromLibFileName(libFileName);
3914+
const resolveFrom = getInferredLibraryNameResolveFrom(options, currentDirectory, libFileName);
39133915
const resolution = actualResolveLibrary(libraryName, resolveFrom, options, libFileName);
39143916
const result: LibResolution = {
39153917
resolution,
@@ -3923,7 +3925,7 @@ export function createProgram(rootNamesOrOptions: readonly string[] | CreateProg
39233925

39243926
function processLibReferenceDirectives(file: SourceFile) {
39253927
forEach(file.libReferenceDirectives, (libReference, index) => {
3926-
const { libName, libFileName } = getLibFileName(libReference);
3928+
const { libName, libFileName } = getLibFileNameFromLibReference(libReference);
39273929
if (libFileName) {
39283930
// we ignore any 'no-default-lib' reference set on this file.
39293931
processRootFile(pathForLibFile(libFileName), /*isDefaultLib*/ true, /*ignoreNoDefaultLib*/ true, { kind: FileIncludeKind.LibReferenceDirective, file: file.path, index, });

src/compiler/resolutionCache.ts

+2-2
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ import {
2626
GetCanonicalFileName,
2727
getDirectoryPath,
2828
getEffectiveTypeRoots,
29-
getInferredLibrarayNameResolveFrom,
29+
getInferredLibraryNameResolveFrom,
3030
getNormalizedAbsolutePath,
3131
getOptionsForLibraryResolution,
3232
getPathComponents,
@@ -591,7 +591,7 @@ export function createResolutionCache(resolutionHost: ResolutionCacheHost, rootD
591591
if (!newProgram?.resolvedLibReferences?.has(libFileName)) {
592592
stopWatchFailedLookupLocationOfResolution(
593593
resolution,
594-
resolutionHost.toPath(getInferredLibrarayNameResolveFrom(newProgram!.getCompilerOptions(), getCurrentDirectory(), libFileName)),
594+
resolutionHost.toPath(getInferredLibraryNameResolveFrom(newProgram!.getCompilerOptions(), getCurrentDirectory(), libFileName)),
595595
getResolvedModule,
596596
);
597597
resolvedLibraries.delete(libFileName);

src/compiler/watch.ts

+33-3
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,8 @@ import {
5656
getDefaultLibFileName,
5757
getDirectoryPath,
5858
getEmitScriptTarget,
59+
getLibFileNameFromLibReference,
60+
getLibraryNameFromLibFileName,
5961
getLineAndCharacterOfPosition,
6062
getNewLineCharacter,
6163
getNormalizedAbsolutePath,
@@ -476,8 +478,18 @@ export function fileIncludeReasonToDiagnostics(program: Program, reason: FileInc
476478
break;
477479
case FileIncludeKind.LibReferenceDirective:
478480
Debug.assert(!referenceLocation.packageId);
479-
message = Diagnostics.Library_referenced_via_0_from_file_1;
480-
break;
481+
const file = Debug.checkDefined(program.getSourceFileByPath(reason.file));
482+
const { libFileName } = getLibFileNameFromLibReference(file.libReferenceDirectives[reason.index]);
483+
const importName = getLibraryImportName(program, libFileName!);
484+
return chainDiagnosticMessages(
485+
/*details*/ undefined,
486+
importName ?
487+
Diagnostics.Library_referenced_via_0_from_file_1_and_imported_via_2 :
488+
Diagnostics.Library_referenced_via_0_from_file_1,
489+
referenceText,
490+
toFileName(referenceLocation.file, fileNameConvertor),
491+
importName!
492+
);
481493
default:
482494
Debug.assertNever(reason);
483495
}
@@ -536,7 +548,18 @@ export function fileIncludeReasonToDiagnostics(program: Program, reason: FileInc
536548
return chainDiagnosticMessages(/*details*/ undefined, ...messageAndArgs);
537549
}
538550
case FileIncludeKind.LibFile: {
539-
if (reason.index !== undefined) return chainDiagnosticMessages(/*details*/ undefined, Diagnostics.Library_0_specified_in_compilerOptions, options.lib![reason.index]);
551+
if (reason.index !== undefined) {
552+
const libFileName = options.lib![reason.index];
553+
const importName = getLibraryImportName(program, libFileName);
554+
return chainDiagnosticMessages(
555+
/*details*/ undefined,
556+
importName ?
557+
Diagnostics.Library_0_specified_in_compilerOptions_and_imported_via_1 :
558+
Diagnostics.Library_0_specified_in_compilerOptions,
559+
libFileName,
560+
importName!
561+
);
562+
}
540563
const target = forEachEntry(targetOptionDeclaration.type, (value, key) => value === getEmitScriptTarget(options) ? key : undefined);
541564
const messageAndArgs: DiagnosticAndArguments = target ? [Diagnostics.Default_library_for_target_0, target] : [Diagnostics.Default_library];
542565
return chainDiagnosticMessages(/*details*/ undefined, ...messageAndArgs);
@@ -546,6 +569,13 @@ export function fileIncludeReasonToDiagnostics(program: Program, reason: FileInc
546569
}
547570
}
548571

572+
function getLibraryImportName(program: Program, libFileName: string) {
573+
const resolved = program.resolvedLibReferences!.get(libFileName);
574+
return resolved?.resolution.resolvedModule?.resolvedFileName === resolved?.actual ?
575+
getLibraryNameFromLibFileName(libFileName) :
576+
undefined;
577+
}
578+
549579
function toFileName(file: SourceFile | string, fileNameConvertor?: (fileName: string) => string) {
550580
const fileName = isString(file) ? file : file.fileName;
551581
return fileNameConvertor ? fileNameConvertor(fileName) : fileName;

tests/baselines/reference/tsbuild/libraryResolution/with-config-with-redirection.js

+8-8
Original file line numberDiff line numberDiff line change
@@ -179,9 +179,9 @@ File '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts' exists - u
179179
Resolving real path for '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts', result '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'.
180180
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
181181
node_modules/@typescript/lib-es5/index.d.ts
182-
Library 'lib.es5.d.ts' specified in compilerOptions
182+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
183183
node_modules/@typescript/lib-dom/index.d.ts
184-
Library 'lib.dom.d.ts' specified in compilerOptions
184+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
185185
project1/core.d.ts
186186
Matched by default include pattern '**/*'
187187
project1/file.ts
@@ -212,9 +212,9 @@ Scoped package detected, looking in 'typescript__lib-dom'
212212
Resolution for module '@typescript/lib-dom' was found in cache from location '/home/src/projects'.
213213
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
214214
node_modules/@typescript/lib-es5/index.d.ts
215-
Library 'lib.es5.d.ts' specified in compilerOptions
215+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
216216
node_modules/@typescript/lib-dom/index.d.ts
217-
Library 'lib.dom.d.ts' specified in compilerOptions
217+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
218218
project2/index.ts
219219
Matched by default include pattern '**/*'
220220
project2/utils.d.ts
@@ -238,9 +238,9 @@ Scoped package detected, looking in 'typescript__lib-dom'
238238
Resolution for module '@typescript/lib-dom' was found in cache from location '/home/src/projects'.
239239
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
240240
node_modules/@typescript/lib-es5/index.d.ts
241-
Library 'lib.es5.d.ts' specified in compilerOptions
241+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
242242
node_modules/@typescript/lib-dom/index.d.ts
243-
Library 'lib.dom.d.ts' specified in compilerOptions
243+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
244244
project3/index.ts
245245
Matched by default include pattern '**/*'
246246
project3/utils.d.ts
@@ -271,9 +271,9 @@ Scoped package detected, looking in 'typescript__lib-dom'
271271
Resolution for module '@typescript/lib-dom' was found in cache from location '/home/src/projects'.
272272
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
273273
node_modules/@typescript/lib-esnext/index.d.ts
274-
Library 'lib.esnext.d.ts' specified in compilerOptions
274+
Library 'lib.esnext.d.ts' specified in compilerOptions and imported via '@typescript/lib-esnext'
275275
node_modules/@typescript/lib-dom/index.d.ts
276-
Library 'lib.dom.d.ts' specified in compilerOptions
276+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
277277
project4/index.ts
278278
Matched by default include pattern '**/*'
279279
project4/utils.d.ts

tests/baselines/reference/tsbuildWatch/libraryResolution/with-config-with-redirection.js

+8-8
Original file line numberDiff line numberDiff line change
@@ -165,9 +165,9 @@ File '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts' exists - u
165165
Resolving real path for '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts', result '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'.
166166
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
167167
node_modules/@typescript/lib-es5/index.d.ts
168-
Library 'lib.es5.d.ts' specified in compilerOptions
168+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
169169
node_modules/@typescript/lib-dom/index.d.ts
170-
Library 'lib.dom.d.ts' specified in compilerOptions
170+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
171171
project1/core.d.ts
172172
Matched by default include pattern '**/*'
173173
project1/file.ts
@@ -198,9 +198,9 @@ Scoped package detected, looking in 'typescript__lib-dom'
198198
Resolution for module '@typescript/lib-dom' was found in cache from location '/home/src/projects'.
199199
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
200200
node_modules/@typescript/lib-es5/index.d.ts
201-
Library 'lib.es5.d.ts' specified in compilerOptions
201+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
202202
node_modules/@typescript/lib-dom/index.d.ts
203-
Library 'lib.dom.d.ts' specified in compilerOptions
203+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
204204
project2/index.ts
205205
Matched by default include pattern '**/*'
206206
project2/utils.d.ts
@@ -224,9 +224,9 @@ Scoped package detected, looking in 'typescript__lib-dom'
224224
Resolution for module '@typescript/lib-dom' was found in cache from location '/home/src/projects'.
225225
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
226226
node_modules/@typescript/lib-es5/index.d.ts
227-
Library 'lib.es5.d.ts' specified in compilerOptions
227+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
228228
node_modules/@typescript/lib-dom/index.d.ts
229-
Library 'lib.dom.d.ts' specified in compilerOptions
229+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
230230
project3/index.ts
231231
Matched by default include pattern '**/*'
232232
project3/utils.d.ts
@@ -257,9 +257,9 @@ Scoped package detected, looking in 'typescript__lib-dom'
257257
Resolution for module '@typescript/lib-dom' was found in cache from location '/home/src/projects'.
258258
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
259259
node_modules/@typescript/lib-esnext/index.d.ts
260-
Library 'lib.esnext.d.ts' specified in compilerOptions
260+
Library 'lib.esnext.d.ts' specified in compilerOptions and imported via '@typescript/lib-esnext'
261261
node_modules/@typescript/lib-dom/index.d.ts
262-
Library 'lib.dom.d.ts' specified in compilerOptions
262+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
263263
project4/index.ts
264264
Matched by default include pattern '**/*'
265265
project4/utils.d.ts

tests/baselines/reference/tsc/libraryResolution/with-config-with-redirection.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -169,9 +169,9 @@ File '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts' exists - u
169169
Resolving real path for '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts', result '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'.
170170
======== Module name '@typescript/lib-dom' was successfully resolved to '/home/src/projects/node_modules/@typescript/lib-dom/index.d.ts'. ========
171171
node_modules/@typescript/lib-es5/index.d.ts
172-
Library 'lib.es5.d.ts' specified in compilerOptions
172+
Library 'lib.es5.d.ts' specified in compilerOptions and imported via '@typescript/lib-es5'
173173
node_modules/@typescript/lib-dom/index.d.ts
174-
Library 'lib.dom.d.ts' specified in compilerOptions
174+
Library 'lib.dom.d.ts' specified in compilerOptions and imported via '@typescript/lib-dom'
175175
project1/core.d.ts
176176
Matched by default include pattern '**/*'
177177
project1/file.ts

0 commit comments

Comments
 (0)