From 90e9c587ee074eb2f3a77d39a03c53526e5895a1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Nicol=C3=B2=20Ribaudo?= Date: Wed, 16 Aug 2023 13:26:46 +0200 Subject: [PATCH] Implement `import defer` parsing support (#15845) --- .../import-phases/defer-declaration/input.js | 1 + .../import-phases/defer-declaration/output.js | 1 + .../test/fixtures/import-phases/options.json | 2 +- packages/babel-parser/data/schema.json | 1 + .../src/parse-error/standard-errors.ts | 6 ++- .../babel-parser/src/parser/expression.ts | 25 +++++++--- packages/babel-parser/src/parser/statement.ts | 24 +++++++--- packages/babel-parser/src/tokenizer/types.ts | 1 + packages/babel-parser/src/types.d.ts | 4 +- packages/babel-parser/src/typings.d.ts | 1 + .../.attributes-expression/input.js | 1 + .../.attributes-expression/options.json | 4 ++ .../input.js | 1 + .../options.json | 4 ++ .../.dynamic-import/input.js | 1 + .../.dynamic-import/options.json | 4 ++ .../attributes-declaration/input.js | 1 + .../attributes-declaration/options.json | 3 ++ .../import-defer/input.js | 1 + .../import-defer/output.json | 38 +++++++++++++++ .../no-default/input.js | 1 + .../no-default/output.json | 41 +++++++++++++++++ .../no-named/input.js | 1 + .../no-named/output.json | 46 +++++++++++++++++++ .../deferred-import-evaluation/options.json | 4 ++ .../babel-parser/typings/babel-parser.d.ts | 1 + .../src/ast-types/generated/index.ts | 4 +- packages/babel-types/src/definitions/core.ts | 4 +- 28 files changed, 204 insertions(+), 22 deletions(-) create mode 100644 packages/babel-generator/test/fixtures/import-phases/defer-declaration/input.js create mode 100644 packages/babel-generator/test/fixtures/import-phases/defer-declaration/output.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/options.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/options.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/options.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/options.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/output.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/output.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/input.js create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/output.json create mode 100644 packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/options.json diff --git a/packages/babel-generator/test/fixtures/import-phases/defer-declaration/input.js b/packages/babel-generator/test/fixtures/import-phases/defer-declaration/input.js new file mode 100644 index 000000000000..299f170b49a3 --- /dev/null +++ b/packages/babel-generator/test/fixtures/import-phases/defer-declaration/input.js @@ -0,0 +1 @@ +import defer * as x from "y"; diff --git a/packages/babel-generator/test/fixtures/import-phases/defer-declaration/output.js b/packages/babel-generator/test/fixtures/import-phases/defer-declaration/output.js new file mode 100644 index 000000000000..dec48ebcce1a --- /dev/null +++ b/packages/babel-generator/test/fixtures/import-phases/defer-declaration/output.js @@ -0,0 +1 @@ +import defer * as x from "y"; \ No newline at end of file diff --git a/packages/babel-generator/test/fixtures/import-phases/options.json b/packages/babel-generator/test/fixtures/import-phases/options.json index dd7da3eefb1a..10acd974a9c4 100644 --- a/packages/babel-generator/test/fixtures/import-phases/options.json +++ b/packages/babel-generator/test/fixtures/import-phases/options.json @@ -1,4 +1,4 @@ { - "plugins": ["sourcePhaseImports"], + "plugins": ["sourcePhaseImports", "deferredImportEvaluation"], "parserOpts": { "createImportExpressions": true } } diff --git a/packages/babel-parser/data/schema.json b/packages/babel-parser/data/schema.json index ad149875ab72..6587bfb879a4 100644 --- a/packages/babel-parser/data/schema.json +++ b/packages/babel-parser/data/schema.json @@ -163,6 +163,7 @@ "decorators", "decorators-legacy", "decoratorAutoAccessors", + "deferredImportEvaluation", "destructuringPrivate", "doExpressions", "dynamicImport", diff --git a/packages/babel-parser/src/parse-error/standard-errors.ts b/packages/babel-parser/src/parse-error/standard-errors.ts index 4ef15c72a1b0..d7c3586c29f6 100644 --- a/packages/babel-parser/src/parse-error/standard-errors.ts +++ b/packages/babel-parser/src/parse-error/standard-errors.ts @@ -66,6 +66,8 @@ export default { "Decorators must be placed *after* the 'export' keyword. Remove the 'decoratorsBeforeExport: false' option to use the '@decorator export class {}' syntax.", DecoratorSemicolon: "Decorators must not be followed by a semicolon.", DecoratorStaticBlock: "Decorators can't be used with a static block.", + DeferImportRequiresNamespace: + 'Only `import defer * as x from "./module"` is valid.', DeletePrivateField: "Deleting a private field is not allowed.", DestructureNamedImport: "ES2015 named imports do not destructure. Use another statement for destructuring after the import.", @@ -75,6 +77,8 @@ export default { `\`${exportName}\` has already been exported. Exported identifiers must be unique.`, DuplicateProto: "Redefinition of __proto__ property.", DuplicateRegExpFlags: "Duplicate regular expression flag.", + DynamicImportPhaseRequiresImportExpressions: ({ phase }: { phase: string }) => + `'import.${phase}(...)' can only be parsed when using the 'createImportExpressions' option.`, ElementAfterRest: "Rest element must be last element.", EscapedCharNotAnIdentifier: "Invalid Unicode escape.", ExportBindingIsString: ({ @@ -235,8 +239,6 @@ export default { "In non-strict mode code, functions can only be declared at top level, inside a block, or as the body of an if statement.", SourcePhaseImportRequiresDefault: 'Only `import source x from "./module"` is valid.', - SourcePhaseDynamicImportRequiresImportExpressions: - "'import.source(...)' can only be parsed when using the 'createImportExpressions' option.", StaticPrototype: "Classes may not have static property named prototype.", SuperNotAllowed: "`super()` is only valid inside a class constructor of a subclass. Maybe a typo in the method name ('constructor') or not extending another class?", diff --git a/packages/babel-parser/src/parser/expression.ts b/packages/babel-parser/src/parser/expression.ts index 7a75141a5a1e..b72d23b0291d 100644 --- a/packages/babel-parser/src/parser/expression.ts +++ b/packages/babel-parser/src/parser/expression.ts @@ -1667,16 +1667,27 @@ export default abstract class ExpressionParser extends LValParser { this.raise(Errors.ImportMetaOutsideModule, { at: id }); } this.sawUnambiguousESM = true; - } else if (this.isContextual(tt._source)) { - this.expectPlugin("sourcePhaseImports"); + } else if (this.isContextual(tt._source) || this.isContextual(tt._defer)) { + const isSource = this.isContextual(tt._source); + + // TODO: The proposal doesn't mention import.defer yet because it was + // pending on a decision for import.source. Wait to enable it until it's + // included in the proposal. + if (!isSource) this.unexpected(); + + this.expectPlugin( + isSource ? "sourcePhaseImports" : "deferredImportEvaluation", + ); if (!this.options.createImportExpressions) { - throw this.raise( - Errors.SourcePhaseDynamicImportRequiresImportExpressions, - { at: this.state.startLoc }, - ); + throw this.raise(Errors.DynamicImportPhaseRequiresImportExpressions, { + at: this.state.startLoc, + phase: this.state.value, + }); } this.next(); - (node as Undone).phase = "source"; + (node as Undone).phase = isSource + ? "source" + : "defer"; return this.parseImportCall(node as Undone); } diff --git a/packages/babel-parser/src/parser/statement.ts b/packages/babel-parser/src/parser/statement.ts index 26d42f209a2c..86a3a4f0552b 100644 --- a/packages/babel-parser/src/parser/statement.ts +++ b/packages/babel-parser/src/parser/statement.ts @@ -2871,18 +2871,23 @@ export default abstract class StatementParser extends ExpressionParser { checkImportReflection(node: Undone) { const { specifiers } = node; - const isSingleDefaultBinding = - specifiers.length === 1 && - specifiers[0].type === "ImportDefaultSpecifier"; + const singleBindingType = + specifiers.length === 1 ? specifiers[0].type : null; if (node.phase === "source") { - if (!isSingleDefaultBinding) { + if (singleBindingType !== "ImportDefaultSpecifier") { this.raise(Errors.SourcePhaseImportRequiresDefault, { at: specifiers[0].loc.start, }); } + } else if (node.phase === "defer") { + if (singleBindingType !== "ImportNamespaceSpecifier") { + this.raise(Errors.DeferImportRequiresNamespace, { + at: specifiers[0].loc.start, + }); + } } else if (node.module) { - if (!isSingleDefaultBinding) { + if (singleBindingType !== "ImportDefaultSpecifier") { this.raise(Errors.ImportReflectionNotBinding, { at: specifiers[0].loc.start, }); @@ -2930,7 +2935,11 @@ export default abstract class StatementParser extends ExpressionParser { isPotentialImportPhase(isExport: boolean): boolean { if (isExport) return false; - return this.isContextual(tt._source) || this.isContextual(tt._module); + return ( + this.isContextual(tt._source) || + this.isContextual(tt._defer) || + this.isContextual(tt._module) + ); } applyImportPhase( @@ -2960,6 +2969,9 @@ export default abstract class StatementParser extends ExpressionParser { if (phase === "source") { this.expectPlugin("sourcePhaseImports", loc); (node as N.ImportDeclaration).phase = "source"; + } else if (phase === "defer") { + this.expectPlugin("deferredImportEvaluation", loc); + (node as N.ImportDeclaration).phase = "defer"; } else if (this.hasPlugin("sourcePhaseImports")) { (node as N.ImportDeclaration).phase = null; } diff --git a/packages/babel-parser/src/tokenizer/types.ts b/packages/babel-parser/src/tokenizer/types.ts index ba621100b069..5e61fd4cd6c6 100644 --- a/packages/babel-parser/src/tokenizer/types.ts +++ b/packages/babel-parser/src/tokenizer/types.ts @@ -284,6 +284,7 @@ export const tt = { _assert: createKeywordLike("assert", { startsExpr }), _async: createKeywordLike("async", { startsExpr }), _await: createKeywordLike("await", { startsExpr }), + _defer: createKeywordLike("defer", { startsExpr }), _from: createKeywordLike("from", { startsExpr }), _get: createKeywordLike("get", { startsExpr }), _let: createKeywordLike("let", { startsExpr }), diff --git a/packages/babel-parser/src/types.d.ts b/packages/babel-parser/src/types.d.ts index 4f2adea24ddb..723ae3969235 100644 --- a/packages/babel-parser/src/types.d.ts +++ b/packages/babel-parser/src/types.d.ts @@ -627,7 +627,7 @@ export interface NewExpression extends CallOrNewBase { export interface ImportExpression extends NodeBase { type: "ImportExpression"; source: Expression; - phase?: null | "source"; + phase?: null | "source" | "defer"; options: Expression | null; } @@ -928,7 +928,7 @@ export interface ImportDeclaration extends NodeBase { >; source: Literal; importKind?: "type" | "typeof" | "value"; // TODO: Not in spec, - phase?: null | "source"; + phase?: null | "source" | "defer"; attributes?: ImportAttribute[]; // @deprecated assertions?: ImportAttribute[]; diff --git a/packages/babel-parser/src/typings.d.ts b/packages/babel-parser/src/typings.d.ts index 126a6c1286d7..c09ff4bb6357 100644 --- a/packages/babel-parser/src/typings.d.ts +++ b/packages/babel-parser/src/typings.d.ts @@ -8,6 +8,7 @@ export type Plugin = | "classStaticBlock" // Enabled by default | "decimal" | "decorators-legacy" + | "deferredImportEvaluation" | "decoratorAutoAccessors" | "destructuringPrivate" | "doExpressions" diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/input.js new file mode 100644 index 000000000000..999759d1e2a8 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/input.js @@ -0,0 +1 @@ +import.defer("x", { with: { attr: "val" } }); diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/options.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/options.json new file mode 100644 index 000000000000..627cd6be3d4a --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.attributes-expression/options.json @@ -0,0 +1,4 @@ +{ + "plugins": ["deferredImportEvaluation", "importAttributes"], + "createImportExpressions": true +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/input.js new file mode 100644 index 000000000000..c483908f6f72 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/input.js @@ -0,0 +1 @@ +import.defer("foo"); \ No newline at end of file diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/options.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/options.json new file mode 100644 index 000000000000..c5b71ea2c3f1 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import-no-createImportExpressions/options.json @@ -0,0 +1,4 @@ +{ + "plugins": ["deferredImportEvaluation"], + "throws": "TODO (disabled test)" +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/input.js new file mode 100644 index 000000000000..c483908f6f72 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/input.js @@ -0,0 +1 @@ +import.defer("foo"); \ No newline at end of file diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/options.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/options.json new file mode 100644 index 000000000000..b057e9868bd8 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/.dynamic-import/options.json @@ -0,0 +1,4 @@ +{ + "plugins": ["deferredImportEvaluation"], + "createImportExpressions": true +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/input.js new file mode 100644 index 000000000000..9bef8e8bfb01 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/input.js @@ -0,0 +1 @@ +import defer * as ns from "x" with { attr: "val" }; \ No newline at end of file diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/options.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/options.json new file mode 100644 index 000000000000..99bb10c43580 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/attributes-declaration/options.json @@ -0,0 +1,3 @@ +{ + "throws": "This experimental syntax requires enabling the parser plugin: \"importAttributes\". (1:35)" +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/input.js new file mode 100644 index 000000000000..806ae2bb7690 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/input.js @@ -0,0 +1 @@ +import defer * as ns from "x"; diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/output.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/output.json new file mode 100644 index 000000000000..104782488e64 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/import-defer/output.json @@ -0,0 +1,38 @@ +{ + "type": "File", + "start":0,"end":30,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":30,"index":30}}, + "program": { + "type": "Program", + "start":0,"end":30,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":30,"index":30}}, + "sourceType": "module", + "interpreter": null, + "body": [ + { + "type": "ImportDeclaration", + "start":0,"end":30,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":30,"index":30}}, + "phase": "defer", + "specifiers": [ + { + "type": "ImportNamespaceSpecifier", + "start":13,"end":20,"loc":{"start":{"line":1,"column":13,"index":13},"end":{"line":1,"column":20,"index":20}}, + "local": { + "type": "Identifier", + "start":18,"end":20,"loc":{"start":{"line":1,"column":18,"index":18},"end":{"line":1,"column":20,"index":20},"identifierName":"ns"}, + "name": "ns" + } + } + ], + "source": { + "type": "StringLiteral", + "start":26,"end":29,"loc":{"start":{"line":1,"column":26,"index":26},"end":{"line":1,"column":29,"index":29}}, + "extra": { + "rawValue": "x", + "raw": "\"x\"" + }, + "value": "x" + } + } + ], + "directives": [] + } +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/input.js new file mode 100644 index 000000000000..d96ed9fc96e9 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/input.js @@ -0,0 +1 @@ +import defer x from "x"; diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/output.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/output.json new file mode 100644 index 000000000000..6e42515a0db8 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-default/output.json @@ -0,0 +1,41 @@ +{ + "type": "File", + "start":0,"end":24,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":24,"index":24}}, + "errors": [ + "SyntaxError: Only `import defer * as x from \"./module\"` is valid. (1:13)" + ], + "program": { + "type": "Program", + "start":0,"end":24,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":24,"index":24}}, + "sourceType": "module", + "interpreter": null, + "body": [ + { + "type": "ImportDeclaration", + "start":0,"end":24,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":24,"index":24}}, + "phase": "defer", + "specifiers": [ + { + "type": "ImportDefaultSpecifier", + "start":13,"end":14,"loc":{"start":{"line":1,"column":13,"index":13},"end":{"line":1,"column":14,"index":14}}, + "local": { + "type": "Identifier", + "start":13,"end":14,"loc":{"start":{"line":1,"column":13,"index":13},"end":{"line":1,"column":14,"index":14},"identifierName":"x"}, + "name": "x" + } + } + ], + "source": { + "type": "StringLiteral", + "start":20,"end":23,"loc":{"start":{"line":1,"column":20,"index":20},"end":{"line":1,"column":23,"index":23}}, + "extra": { + "rawValue": "x", + "raw": "\"x\"" + }, + "value": "x" + } + } + ], + "directives": [] + } +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/input.js b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/input.js new file mode 100644 index 000000000000..5c307da2a7d5 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/input.js @@ -0,0 +1 @@ +import defer { x } from "x"; diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/output.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/output.json new file mode 100644 index 000000000000..2a8491f68432 --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/no-named/output.json @@ -0,0 +1,46 @@ +{ + "type": "File", + "start":0,"end":28,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":28,"index":28}}, + "errors": [ + "SyntaxError: Only `import defer * as x from \"./module\"` is valid. (1:15)" + ], + "program": { + "type": "Program", + "start":0,"end":28,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":28,"index":28}}, + "sourceType": "module", + "interpreter": null, + "body": [ + { + "type": "ImportDeclaration", + "start":0,"end":28,"loc":{"start":{"line":1,"column":0,"index":0},"end":{"line":1,"column":28,"index":28}}, + "phase": "defer", + "specifiers": [ + { + "type": "ImportSpecifier", + "start":15,"end":16,"loc":{"start":{"line":1,"column":15,"index":15},"end":{"line":1,"column":16,"index":16}}, + "imported": { + "type": "Identifier", + "start":15,"end":16,"loc":{"start":{"line":1,"column":15,"index":15},"end":{"line":1,"column":16,"index":16},"identifierName":"x"}, + "name": "x" + }, + "local": { + "type": "Identifier", + "start":15,"end":16,"loc":{"start":{"line":1,"column":15,"index":15},"end":{"line":1,"column":16,"index":16},"identifierName":"x"}, + "name": "x" + } + } + ], + "source": { + "type": "StringLiteral", + "start":24,"end":27,"loc":{"start":{"line":1,"column":24,"index":24},"end":{"line":1,"column":27,"index":27}}, + "extra": { + "rawValue": "x", + "raw": "\"x\"" + }, + "value": "x" + } + } + ], + "directives": [] + } +} diff --git a/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/options.json b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/options.json new file mode 100644 index 000000000000..acbd3f43609b --- /dev/null +++ b/packages/babel-parser/test/fixtures/experimental/deferred-import-evaluation/options.json @@ -0,0 +1,4 @@ +{ + "sourceType": "module", + "plugins": ["deferredImportEvaluation"] +} diff --git a/packages/babel-parser/typings/babel-parser.d.ts b/packages/babel-parser/typings/babel-parser.d.ts index 54743d7aa382..2ef94c4b79aa 100644 --- a/packages/babel-parser/typings/babel-parser.d.ts +++ b/packages/babel-parser/typings/babel-parser.d.ts @@ -12,6 +12,7 @@ type Plugin = | "classStaticBlock" // Enabled by default | "decimal" | "decorators-legacy" + | "deferredImportEvaluation" | "decoratorAutoAccessors" | "destructuringPrivate" | "doExpressions" diff --git a/packages/babel-types/src/ast-types/generated/index.ts b/packages/babel-types/src/ast-types/generated/index.ts index f0be72934030..a7bad4a23735 100644 --- a/packages/babel-types/src/ast-types/generated/index.ts +++ b/packages/babel-types/src/ast-types/generated/index.ts @@ -864,7 +864,7 @@ export interface ImportDeclaration extends BaseNode { attributes?: Array | null; importKind?: "type" | "typeof" | "value" | null; module?: boolean | null; - phase?: "source" | null; + phase?: "source" | "defer" | null; } export interface ImportDefaultSpecifier extends BaseNode { @@ -888,7 +888,7 @@ export interface ImportExpression extends BaseNode { type: "ImportExpression"; source: Expression; options?: Expression | null; - phase?: "source" | null; + phase?: "source" | "defer" | null; } export interface MetaProperty extends BaseNode { diff --git a/packages/babel-types/src/definitions/core.ts b/packages/babel-types/src/definitions/core.ts index 88dce5d382f6..fbc36acec819 100644 --- a/packages/babel-types/src/definitions/core.ts +++ b/packages/babel-types/src/definitions/core.ts @@ -1745,7 +1745,7 @@ defineType("ImportDeclaration", { }, phase: { default: null, - validate: assertOneOf("source"), + validate: assertOneOf("source", "defer"), }, specifiers: { validate: chain( @@ -1816,7 +1816,7 @@ defineType("ImportExpression", { fields: { phase: { default: null, - validate: assertOneOf("source"), + validate: assertOneOf("source", "defer"), }, source: { validate: assertNodeType("Expression"),