Skip to content

Commit eef7d8b

Browse files
author
Andy
authored
Treat explicit imports from node_modules as external library imports (#16364)
* Treat explicit imports from `node_modules` as external library imports * Update baselines
1 parent babb88a commit eef7d8b

16 files changed

+99
-29
lines changed

src/compiler/checker.ts

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1694,7 +1694,6 @@ namespace ts {
16941694
if (ambientModule) {
16951695
return ambientModule;
16961696
}
1697-
const isRelative = isExternalModuleNameRelative(moduleReference);
16981697
const resolvedModule = getResolvedModule(getSourceFileOfNode(location), moduleReference);
16991698
const resolutionDiagnostic = resolvedModule && getResolutionDiagnostic(compilerOptions, resolvedModule);
17001699
const sourceFile = resolvedModule && !resolutionDiagnostic && host.getSourceFile(resolvedModule.resolvedFileName);
@@ -1718,7 +1717,7 @@ namespace ts {
17181717
}
17191718

17201719
// May be an untyped module. If so, ignore resolutionDiagnostic.
1721-
if (!isRelative && resolvedModule && !extensionIsTypeScript(resolvedModule.extension)) {
1720+
if (resolvedModule && resolvedModule.isExternalLibraryImport && !extensionIsTypeScript(resolvedModule.extension)) {
17221721
if (isForAugmentation) {
17231722
const diag = Diagnostics.Invalid_module_name_in_augmentation_Module_0_resolves_to_an_untyped_module_at_1_which_cannot_be_augmented;
17241723
error(errorNode, diag, moduleReference, resolvedModule.resolvedFileName);

src/compiler/core.ts

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1543,16 +1543,20 @@ namespace ts {
15431543
}
15441544

15451545
export function normalizePath(path: string): string {
1546+
return normalizePathAndParts(path).path;
1547+
}
1548+
1549+
export function normalizePathAndParts(path: string): { path: string, parts: string[] } {
15461550
path = normalizeSlashes(path);
15471551
const rootLength = getRootLength(path);
15481552
const root = path.substr(0, rootLength);
1549-
const normalized = getNormalizedParts(path, rootLength);
1550-
if (normalized.length) {
1551-
const joinedParts = root + normalized.join(directorySeparator);
1552-
return pathEndsWithDirectorySeparator(path) ? joinedParts + directorySeparator : joinedParts;
1553+
const parts = getNormalizedParts(path, rootLength);
1554+
if (parts.length) {
1555+
const joinedParts = root + parts.join(directorySeparator);
1556+
return { path: pathEndsWithDirectorySeparator(path) ? joinedParts + directorySeparator : joinedParts, parts };
15531557
}
15541558
else {
1555-
return root;
1559+
return { path: root, parts };
15561560
}
15571561
}
15581562

src/compiler/moduleNameResolver.ts

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -747,9 +747,10 @@ namespace ts {
747747
return { value: resolvedValue && { resolved: resolvedValue, isExternalLibraryImport: true } };
748748
}
749749
else {
750-
const candidate = normalizePath(combinePaths(containingDirectory, moduleName));
750+
const { path: candidate, parts } = normalizePathAndParts(combinePaths(containingDirectory, moduleName));
751751
const resolved = nodeLoadModuleByRelativeName(extensions, candidate, failedLookupLocations, /*onlyRecordFailures*/ false, state, /*considerPackageJson*/ true);
752-
return resolved && toSearchResult({ resolved, isExternalLibraryImport: false });
752+
// Treat explicit "node_modules" import as an external library import.
753+
return resolved && toSearchResult({ resolved, isExternalLibraryImport: contains(parts, "node_modules") });
753754
}
754755
}
755756
}

src/compiler/types.ts

Lines changed: 1 addition & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -3953,12 +3953,7 @@ namespace ts {
39533953
export interface ResolvedModule {
39543954
/** Path of the file the module was resolved to. */
39553955
resolvedFileName: string;
3956-
/**
3957-
* Denotes if 'resolvedFileName' is isExternalLibraryImport and thus should be a proper external module:
3958-
* - be a .d.ts file
3959-
* - use top level imports\exports
3960-
* - don't use tripleslash references
3961-
*/
3956+
/** True if `resolvedFileName` comes from `node_modules`. */
39623957
isExternalLibraryImport?: boolean;
39633958
}
39643959

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
//// [tests/cases/compiler/moduleResolution_explicitNodeModulesImport.ts] ////
2+
3+
//// [index.js]
4+
exports.x = 0;
5+
6+
//// [index.ts]
7+
import { x } from "../node_modules/foo";
8+
9+
10+
//// [index.js]
11+
"use strict";
12+
exports.__esModule = true;
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
=== /src/index.ts ===
2+
import { x } from "../node_modules/foo";
3+
>x : Symbol(x, Decl(index.ts, 0, 8))
4+
5+
=== /node_modules/foo/index.js ===
6+
exports.x = 0;
7+
>exports : Symbol(x, Decl(index.js, 0, 0))
8+
>x : Symbol(x, Decl(index.js, 0, 0))
9+
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
=== /src/index.ts ===
2+
import { x } from "../node_modules/foo";
3+
>x : number
4+
5+
=== /node_modules/foo/index.js ===
6+
exports.x = 0;
7+
>exports.x = 0 : 0
8+
>exports.x : any
9+
>exports : any
10+
>x : any
11+
>0 : 0
12+
Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
//// [tests/cases/compiler/moduleResolution_explicitNodeModulesImport_implicitAny.ts] ////
2+
3+
//// [index.js]
4+
exports.x = 0;
5+
6+
//// [index.ts]
7+
import { y } from "../node_modules/foo";
8+
9+
10+
//// [index.js]
11+
"use strict";
12+
exports.__esModule = true;
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
=== /src/index.ts ===
2+
import { y } from "../node_modules/foo";
3+
>y : Symbol(y, Decl(index.ts, 0, 8))
4+
Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
=== /src/index.ts ===
2+
import { y } from "../node_modules/foo";
3+
>y : any
4+

tests/baselines/reference/project/nodeModulesMaxDepthExceeded/amd/nodeModulesMaxDepthExceeded.errors.txt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,6 @@ maxDepthExceeded/root.ts(4,4): error TS2540: Cannot assign to 'rel' because it i
1313
"exclude": ["node_modules/m2/**/*"]
1414
}
1515

16-
==== relative.js (0 errors) ====
17-
exports.relativeProp = true;
18-
1916
==== index.js (0 errors) ====
2017
var m2 = require('m2');
2118
var rel = require('./relative');
@@ -51,4 +48,7 @@ maxDepthExceeded/root.ts(4,4): error TS2540: Cannot assign to 'rel' because it i
5148
"b": "hello, world",
5249
"person": m3.person
5350
};
51+
52+
==== relative.js (0 errors) ====
53+
exports.relativeProp = true;
5454

tests/baselines/reference/project/nodeModulesMaxDepthExceeded/amd/nodeModulesMaxDepthExceeded.json

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,14 +7,14 @@
77
"project": "maxDepthExceeded",
88
"resolvedInputFiles": [
99
"lib.d.ts",
10-
"maxDepthExceeded/node_modules/m1/relative.js",
1110
"maxDepthExceeded/node_modules/m1/index.js",
1211
"maxDepthExceeded/root.ts",
13-
"maxDepthExceeded/node_modules/m2/entry.js"
12+
"maxDepthExceeded/node_modules/m2/entry.js",
13+
"maxDepthExceeded/node_modules/m1/relative.js"
1414
],
1515
"emittedFiles": [
16-
"maxDepthExceeded/built/node_modules/m1/relative.js",
1716
"maxDepthExceeded/built/node_modules/m1/index.js",
18-
"maxDepthExceeded/built/root.js"
17+
"maxDepthExceeded/built/root.js",
18+
"maxDepthExceeded/built/node_modules/m1/relative.js"
1919
]
2020
}

tests/baselines/reference/project/nodeModulesMaxDepthExceeded/node/nodeModulesMaxDepthExceeded.errors.txt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,6 @@ maxDepthExceeded/root.ts(4,4): error TS2540: Cannot assign to 'rel' because it i
1313
"exclude": ["node_modules/m2/**/*"]
1414
}
1515

16-
==== relative.js (0 errors) ====
17-
exports.relativeProp = true;
18-
1916
==== index.js (0 errors) ====
2017
var m2 = require('m2');
2118
var rel = require('./relative');
@@ -51,4 +48,7 @@ maxDepthExceeded/root.ts(4,4): error TS2540: Cannot assign to 'rel' because it i
5148
"b": "hello, world",
5249
"person": m3.person
5350
};
51+
52+
==== relative.js (0 errors) ====
53+
exports.relativeProp = true;
5454

tests/baselines/reference/project/nodeModulesMaxDepthExceeded/node/nodeModulesMaxDepthExceeded.json

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,14 +7,14 @@
77
"project": "maxDepthExceeded",
88
"resolvedInputFiles": [
99
"lib.d.ts",
10-
"maxDepthExceeded/node_modules/m1/relative.js",
1110
"maxDepthExceeded/node_modules/m1/index.js",
1211
"maxDepthExceeded/root.ts",
13-
"maxDepthExceeded/node_modules/m2/entry.js"
12+
"maxDepthExceeded/node_modules/m2/entry.js",
13+
"maxDepthExceeded/node_modules/m1/relative.js"
1414
],
1515
"emittedFiles": [
16-
"maxDepthExceeded/built/node_modules/m1/relative.js",
1716
"maxDepthExceeded/built/node_modules/m1/index.js",
18-
"maxDepthExceeded/built/root.js"
17+
"maxDepthExceeded/built/root.js",
18+
"maxDepthExceeded/built/node_modules/m1/relative.js"
1919
]
2020
}
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
// @allowJs: true
2+
// @noImplicitReferences: true
3+
// @maxNodeModuleJsDepth: 1
4+
5+
// @Filename: /node_modules/foo/index.js
6+
exports.x = 0;
7+
8+
// @Filename: /src/index.ts
9+
import { x } from "../node_modules/foo";
Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
// @allowJs: true
2+
// @noImplicitReferences: true
3+
// @maxNodeModuleJsDepth: 0
4+
5+
// @Filename: /node_modules/foo/index.js
6+
exports.x = 0;
7+
8+
// @Filename: /src/index.ts
9+
import { y } from "../node_modules/foo";

0 commit comments

Comments
 (0)