mirror of
https://github.com/microsoft/TypeScript.git
synced 2025-11-18 17:21:48 +00:00
Allow extensionless mains for cjs mode packages even from an esm import (#47893)
This commit is contained in:
@@ -1819,7 +1819,17 @@ namespace ts {
|
||||
// Even if extensions is DtsOnly, we can still look up a .ts file as a result of package.json "types"
|
||||
const nextExtensions = extensions === Extensions.DtsOnly ? Extensions.TypeScript : extensions;
|
||||
// Don't do package.json lookup recursively, because Node.js' package lookup doesn't.
|
||||
return nodeLoadModuleByRelativeName(nextExtensions, candidate, onlyRecordFailures, state, /*considerPackageJson*/ false);
|
||||
|
||||
// Disable `EsmMode` for the resolution of the package path for cjs-mode packages (so the `main` field can omit extensions)
|
||||
// (technically it only emits a deprecation warning in esm packages right now, but that's probably
|
||||
// enough to mean we don't need to support it)
|
||||
const features = state.features;
|
||||
if (jsonContent?.type !== "module") {
|
||||
state.features &= ~NodeResolutionFeatures.EsmMode;
|
||||
}
|
||||
const result = nodeLoadModuleByRelativeName(nextExtensions, candidate, onlyRecordFailures, state, /*considerPackageJson*/ false);
|
||||
state.features = features;
|
||||
return result;
|
||||
};
|
||||
|
||||
const onlyRecordFailuresForPackageFile = packageFile ? !directoryProbablyExists(getDirectoryPath(packageFile), state.host) : undefined;
|
||||
|
||||
@@ -0,0 +1,42 @@
|
||||
//// [tests/cases/compiler/nodeNextEsmImportsOfPackagesWithExtensionlessMains.ts] ////
|
||||
|
||||
//// [package.json]
|
||||
{
|
||||
"name": "@types/ip",
|
||||
"version": "1.1.0",
|
||||
"main": "",
|
||||
"types": "index"
|
||||
}
|
||||
//// [index.d.ts]
|
||||
export function address(): string;
|
||||
//// [package.json]
|
||||
{
|
||||
"name": "nullthrows",
|
||||
"version": "1.1.1",
|
||||
"main": "nullthrows.js",
|
||||
"types": "nullthrows.d.ts"
|
||||
}
|
||||
//// [nullthrows.d.ts]
|
||||
declare function nullthrows(x: any): any;
|
||||
declare namespace nullthrows {
|
||||
export {nullthrows as default};
|
||||
}
|
||||
export = nullthrows;
|
||||
//// [package.json]
|
||||
{
|
||||
"type": "module"
|
||||
}
|
||||
//// [index.ts]
|
||||
import * as ip from 'ip';
|
||||
import nullthrows from 'nullthrows'; // shouldn't be callable, `nullthrows` is a cjs package, so the `default` is the module itself
|
||||
|
||||
export function getAddress(): string {
|
||||
return nullthrows(ip.address());
|
||||
}
|
||||
|
||||
//// [index.js]
|
||||
import * as ip from 'ip';
|
||||
import nullthrows from 'nullthrows'; // shouldn't be callable, `nullthrows` is a cjs package, so the `default` is the module itself
|
||||
export function getAddress() {
|
||||
return nullthrows(ip.address());
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
=== tests/cases/compiler/index.ts ===
|
||||
import * as ip from 'ip';
|
||||
>ip : Symbol(ip, Decl(index.ts, 0, 6))
|
||||
|
||||
import nullthrows from 'nullthrows'; // shouldn't be callable, `nullthrows` is a cjs package, so the `default` is the module itself
|
||||
>nullthrows : Symbol(nullthrows, Decl(index.ts, 1, 6))
|
||||
|
||||
export function getAddress(): string {
|
||||
>getAddress : Symbol(getAddress, Decl(index.ts, 1, 36))
|
||||
|
||||
return nullthrows(ip.address());
|
||||
>nullthrows : Symbol(nullthrows, Decl(index.ts, 1, 6))
|
||||
>ip.address : Symbol(ip.address, Decl(index.d.ts, 0, 0))
|
||||
>ip : Symbol(ip, Decl(index.ts, 0, 6))
|
||||
>address : Symbol(ip.address, Decl(index.d.ts, 0, 0))
|
||||
}
|
||||
=== tests/cases/compiler/node_modules/@types/ip/index.d.ts ===
|
||||
export function address(): string;
|
||||
>address : Symbol(address, Decl(index.d.ts, 0, 0))
|
||||
|
||||
=== tests/cases/compiler/node_modules/nullthrows/nullthrows.d.ts ===
|
||||
declare function nullthrows(x: any): any;
|
||||
>nullthrows : Symbol(nullthrows, Decl(nullthrows.d.ts, 0, 0), Decl(nullthrows.d.ts, 0, 41))
|
||||
>x : Symbol(x, Decl(nullthrows.d.ts, 0, 28))
|
||||
|
||||
declare namespace nullthrows {
|
||||
>nullthrows : Symbol(nullthrows, Decl(nullthrows.d.ts, 0, 0), Decl(nullthrows.d.ts, 0, 41))
|
||||
|
||||
export {nullthrows as default};
|
||||
>nullthrows : Symbol(nullthrows, Decl(nullthrows.d.ts, 0, 0), Decl(nullthrows.d.ts, 0, 41))
|
||||
>default : Symbol(default, Decl(nullthrows.d.ts, 2, 12))
|
||||
}
|
||||
export = nullthrows;
|
||||
>nullthrows : Symbol(nullthrows, Decl(nullthrows.d.ts, 0, 0), Decl(nullthrows.d.ts, 0, 41))
|
||||
|
||||
@@ -0,0 +1,37 @@
|
||||
=== tests/cases/compiler/index.ts ===
|
||||
import * as ip from 'ip';
|
||||
>ip : typeof ip
|
||||
|
||||
import nullthrows from 'nullthrows'; // shouldn't be callable, `nullthrows` is a cjs package, so the `default` is the module itself
|
||||
>nullthrows : typeof nullthrows
|
||||
|
||||
export function getAddress(): string {
|
||||
>getAddress : () => string
|
||||
|
||||
return nullthrows(ip.address());
|
||||
>nullthrows(ip.address()) : any
|
||||
>nullthrows : typeof nullthrows
|
||||
>ip.address() : string
|
||||
>ip.address : () => string
|
||||
>ip : typeof ip
|
||||
>address : () => string
|
||||
}
|
||||
=== tests/cases/compiler/node_modules/@types/ip/index.d.ts ===
|
||||
export function address(): string;
|
||||
>address : () => string
|
||||
|
||||
=== tests/cases/compiler/node_modules/nullthrows/nullthrows.d.ts ===
|
||||
declare function nullthrows(x: any): any;
|
||||
>nullthrows : typeof nullthrows
|
||||
>x : any
|
||||
|
||||
declare namespace nullthrows {
|
||||
>nullthrows : typeof nullthrows
|
||||
|
||||
export {nullthrows as default};
|
||||
>nullthrows : typeof nullthrows
|
||||
>default : typeof nullthrows
|
||||
}
|
||||
export = nullthrows;
|
||||
>nullthrows : typeof nullthrows
|
||||
|
||||
@@ -0,0 +1,36 @@
|
||||
// @noImplicitReferences: true
|
||||
// @module: nodenext
|
||||
// @outDir: esm
|
||||
// @filename: node_modules/@types/ip/package.json
|
||||
{
|
||||
"name": "@types/ip",
|
||||
"version": "1.1.0",
|
||||
"main": "",
|
||||
"types": "index"
|
||||
}
|
||||
// @filename: node_modules/@types/ip/index.d.ts
|
||||
export function address(): string;
|
||||
// @filename: node_modules/nullthrows/package.json
|
||||
{
|
||||
"name": "nullthrows",
|
||||
"version": "1.1.1",
|
||||
"main": "nullthrows.js",
|
||||
"types": "nullthrows.d.ts"
|
||||
}
|
||||
// @filename: node_modules/nullthrows/nullthrows.d.ts
|
||||
declare function nullthrows(x: any): any;
|
||||
declare namespace nullthrows {
|
||||
export {nullthrows as default};
|
||||
}
|
||||
export = nullthrows;
|
||||
// @filename: package.json
|
||||
{
|
||||
"type": "module"
|
||||
}
|
||||
// @filename: index.ts
|
||||
import * as ip from 'ip';
|
||||
import nullthrows from 'nullthrows'; // shouldn't be callable, `nullthrows` is a cjs package, so the `default` is the module itself
|
||||
|
||||
export function getAddress(): string {
|
||||
return nullthrows(ip.address());
|
||||
}
|
||||
Reference in New Issue
Block a user