Reuse existing module specifiers in js declaration emit (#52089)

This commit is contained in:
Wesley Wigham
2023-01-09 10:15:42 -08:00
committed by GitHub
parent 11bc7b758d
commit 00567618bd
9 changed files with 202 additions and 19 deletions
+18 -12
View File
@@ -8999,25 +8999,28 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
// Is bound into file.symbol.globalExports instead, which we don't currently traverse
addResult(factory.createNamespaceExportDeclaration(idText((node as NamespaceExportDeclaration).name)), ModifierFlags.None);
break;
case SyntaxKind.ImportClause:
case SyntaxKind.ImportClause: {
const generatedSpecifier = getSpecifierForModuleSymbol(target.parent || target, context); // generate specifier (even though we're reusing and existing one) for ambient module reference include side effects
const specifier = bundled ? factory.createStringLiteral(generatedSpecifier) : (node as ImportClause).parent.moduleSpecifier;
addResult(factory.createImportDeclaration(
/*modifiers*/ undefined,
factory.createImportClause(/*isTypeOnly*/ false, factory.createIdentifier(localName), /*namedBindings*/ undefined),
// We use `target.parent || target` below as `target.parent` is unset when the target is a module which has been export assigned
// And then made into a default by the `esModuleInterop` or `allowSyntheticDefaultImports` flag
// In such cases, the `target` refers to the module itself already
factory.createStringLiteral(getSpecifierForModuleSymbol(target.parent || target, context)),
/*assertClause*/ undefined
specifier,
(node as ImportClause).parent.assertClause
), ModifierFlags.None);
break;
case SyntaxKind.NamespaceImport:
}
case SyntaxKind.NamespaceImport: {
const generatedSpecifier = getSpecifierForModuleSymbol(target.parent || target, context); // generate specifier (even though we're reusing and existing one) for ambient module reference include side effects
const specifier = bundled ? factory.createStringLiteral(generatedSpecifier) : (node as NamespaceImport).parent.parent.moduleSpecifier;
addResult(factory.createImportDeclaration(
/*modifiers*/ undefined,
factory.createImportClause(/*isTypeOnly*/ false, /*importClause*/ undefined, factory.createNamespaceImport(factory.createIdentifier(localName))),
factory.createStringLiteral(getSpecifierForModuleSymbol(target, context)),
/*assertClause*/ undefined
specifier,
(node as NamespaceImport).parent.parent.assertClause
), ModifierFlags.None);
break;
}
case SyntaxKind.NamespaceExport:
addResult(factory.createExportDeclaration(
/*modifiers*/ undefined,
@@ -9026,7 +9029,9 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
factory.createStringLiteral(getSpecifierForModuleSymbol(target, context))
), ModifierFlags.None);
break;
case SyntaxKind.ImportSpecifier:
case SyntaxKind.ImportSpecifier: {
const generatedSpecifier = getSpecifierForModuleSymbol(target.parent || target, context); // generate specifier (even though we're reusing and existing one) for ambient module reference include side effects
const specifier = bundled ? factory.createStringLiteral(generatedSpecifier) : (node as ImportSpecifier).parent.parent.parent.moduleSpecifier;
addResult(factory.createImportDeclaration(
/*modifiers*/ undefined,
factory.createImportClause(
@@ -9039,10 +9044,11 @@ export function createTypeChecker(host: TypeCheckerHost): TypeChecker {
factory.createIdentifier(localName)
)
])),
factory.createStringLiteral(getSpecifierForModuleSymbol(target.parent || target, context)),
/*assertClause*/ undefined
specifier,
(node as ImportSpecifier).parent.parent.parent.assertClause,
), ModifierFlags.None);
break;
}
case SyntaxKind.ExportSpecifier:
// does not use localName because the symbol name in this case refers to the name in the exports table,
// which we must exactly preserve
@@ -77,7 +77,7 @@ export class Foo3 extends d {
}
export class Foo4 extends c {
}
import { EventEmitter } from "events";
import { n3 } from "nestNamespaceModule";
import { d } from "nestNamespaceModule";
import { c } from "renameModule";
import { EventEmitter } from 'events';
import { n3 } from 'nestNamespaceModule';
import { d } from 'nestNamespaceModule';
import { c } from 'renameModule';
@@ -0,0 +1,84 @@
//// [tests/cases/compiler/jsDeclarationEmitExportedClassWithExtends.ts] ////
//// [package.json]
{
"name": "lit",
"version": "0.0.1",
"type": "module",
"exports": {
".": {
"types": "./development/index.d.ts"
}
}
}
//// [index.d.ts]
export * from "lit-element/lit-element.js";
//// [package.json]
{
"name": "lit-element",
"version": "0.0.1",
"type": "module",
"exports": {
".": {
"types": "./development/index.d.ts"
},
"./lit-element.js": {
"types": "./development/lit-element.d.ts"
}
}
}
//// [index.d.ts]
export * from "./lit-element.js";
//// [lit-element.d.ts]
export class LitElement {}
//// [package.json]
{
"type": "module",
"private": true
}
//// [index.js]
import { LitElement, LitElement as LitElement2 } from "lit";
export class ElementB extends LitElement {}
export class ElementC extends LitElement2 {}
//// [index.js]
var __extends = (this && this.__extends) || (function () {
var extendStatics = function (d, b) {
extendStatics = Object.setPrototypeOf ||
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
function (d, b) { for (var p in b) if (Object.prototype.hasOwnProperty.call(b, p)) d[p] = b[p]; };
return extendStatics(d, b);
};
return function (d, b) {
if (typeof b !== "function" && b !== null)
throw new TypeError("Class extends value " + String(b) + " is not a constructor or null");
extendStatics(d, b);
function __() { this.constructor = d; }
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
};
})();
import { LitElement, LitElement as LitElement2 } from "lit";
var ElementB = /** @class */ (function (_super) {
__extends(ElementB, _super);
function ElementB() {
return _super !== null && _super.apply(this, arguments) || this;
}
return ElementB;
}(LitElement));
export { ElementB };
var ElementC = /** @class */ (function (_super) {
__extends(ElementC, _super);
function ElementC() {
return _super !== null && _super.apply(this, arguments) || this;
}
return ElementC;
}(LitElement2));
export { ElementC };
//// [index.d.ts]
export class ElementB extends LitElement {
}
export class ElementC extends LitElement {
}
import { LitElement } from "lit";
@@ -0,0 +1,24 @@
=== tests/cases/compiler/node_modules/lit/development/index.d.ts ===
export * from "lit-element/lit-element.js";
=== tests/cases/compiler/node_modules/lit-element/development/index.d.ts ===
export * from "./lit-element.js";
=== tests/cases/compiler/node_modules/lit-element/development/lit-element.d.ts ===
export class LitElement {}
>LitElement : Symbol(LitElement, Decl(lit-element.d.ts, 0, 0))
=== tests/cases/compiler/index.js ===
import { LitElement, LitElement as LitElement2 } from "lit";
>LitElement : Symbol(LitElement, Decl(index.js, 0, 8))
>LitElement : Symbol(LitElement, Decl(lit-element.d.ts, 0, 0))
>LitElement2 : Symbol(LitElement2, Decl(index.js, 0, 20))
export class ElementB extends LitElement {}
>ElementB : Symbol(ElementB, Decl(index.js, 0, 60))
>LitElement : Symbol(LitElement, Decl(index.js, 0, 8))
export class ElementC extends LitElement2 {}
>ElementC : Symbol(ElementC, Decl(index.js, 1, 43))
>LitElement2 : Symbol(LitElement2, Decl(index.js, 0, 20))
@@ -0,0 +1,24 @@
=== tests/cases/compiler/node_modules/lit/development/index.d.ts ===
export * from "lit-element/lit-element.js";
=== tests/cases/compiler/node_modules/lit-element/development/index.d.ts ===
export * from "./lit-element.js";
=== tests/cases/compiler/node_modules/lit-element/development/lit-element.d.ts ===
export class LitElement {}
>LitElement : LitElement
=== tests/cases/compiler/index.js ===
import { LitElement, LitElement as LitElement2 } from "lit";
>LitElement : typeof LitElement
>LitElement : typeof LitElement
>LitElement2 : typeof LitElement
export class ElementB extends LitElement {}
>ElementB : ElementB
>LitElement : LitElement
export class ElementC extends LitElement2 {}
>ElementC : ElementC
>LitElement2 : LitElement
@@ -83,7 +83,7 @@ export namespace testFnTypes {
* @returns {number|null} Result.
*/
export function testFn(input: testFnTypes.input): number | null;
import { myTypes } from "./file.js";
import { myTypes } from './file.js';
/**
* @namespace testFnTypes
* @global
@@ -243,4 +243,4 @@ declare namespace Tree {
export const parentSource: string;
}
}
import PropTypes from "prop-types";
import PropTypes from 'prop-types';
@@ -39,4 +39,4 @@ declare namespace defaultProps {
const bar_1: boolean;
export { bar_1 as bar };
}
import PropTypes from "prop-types";
import PropTypes from 'prop-types';
@@ -0,0 +1,45 @@
// @checkJs: true
// @outDir: tests/cases/compiler/out
// @declaration: true
// @module: esnext
// @moduleResolution: nodenext
// @filename: node_modules/lit/package.json
{
"name": "lit",
"version": "0.0.1",
"type": "module",
"exports": {
".": {
"types": "./development/index.d.ts"
}
}
}
// @filename: node_modules/lit/development/index.d.ts
export * from "lit-element/lit-element.js";
// @filename: node_modules/lit-element/package.json
{
"name": "lit-element",
"version": "0.0.1",
"type": "module",
"exports": {
".": {
"types": "./development/index.d.ts"
},
"./lit-element.js": {
"types": "./development/lit-element.d.ts"
}
}
}
// @filename: node_modules/lit-element/development/index.d.ts
export * from "./lit-element.js";
// @filename: node_modules/lit-element/development//lit-element.d.ts
export class LitElement {}
// @filename: package.json
{
"type": "module",
"private": true
}
// @filename: index.js
import { LitElement, LitElement as LitElement2 } from "lit";
export class ElementB extends LitElement {}
export class ElementC extends LitElement2 {}