Parse JS Module Blocks proposal (#12469)

This commit is contained in:
Sosuke Suzuki 2021-02-22 04:08:20 +09:00 committed by GitHub
parent e4588bed22
commit 9c567baa9b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
64 changed files with 1704 additions and 32 deletions

View File

@ -300,3 +300,16 @@ export function V8IntrinsicIdentifier(
this.token("%"); this.token("%");
this.word(node.name); this.word(node.name);
} }
export function ModuleExpression(node: t.ModuleExpression) {
this.word("module");
this.space();
this.token("{");
if (node.body.body.length === 0) {
this.token("}");
} else {
this.newline();
this.printSequence(node.body.body, node, { indent: true });
this.rightBrace();
}
}

View File

@ -0,0 +1,6 @@
const m = module { export const foo = "foo" };
module {
foo;
bar;
};
foo(module {});

View File

@ -0,0 +1,4 @@
{
"plugins": ["moduleBlocks"],
"sourceType": "module"
}

View File

@ -0,0 +1,8 @@
const m = module {
export const foo = "foo";
};
module {
foo;
bar;
};
foo(module {});

View File

@ -87,6 +87,7 @@ These are the core @babel/parser (babylon) AST node types.
- [SequenceExpression](#sequenceexpression) - [SequenceExpression](#sequenceexpression)
- [ParenthesizedExpression](#parenthesizedexpression) - [ParenthesizedExpression](#parenthesizedexpression)
- [DoExpression](#doexpression) - [DoExpression](#doexpression)
- [ModuleExpression](#moduleexpression)
- [Template Literals](#template-literals) - [Template Literals](#template-literals)
- [TemplateLiteral](#templateliteral) - [TemplateLiteral](#templateliteral)
- [TaggedTemplateExpression](#taggedtemplateexpression) - [TaggedTemplateExpression](#taggedtemplateexpression)
@ -1086,6 +1087,17 @@ interface DoExpression <: Expression {
} }
``` ```
## ModuleExpression
```js
interface ModuleExpression <: Expression {
type: "ModuleExpression";
body: Program
}
```
A inline module expression proposed in https://github.com/tc39/proposal-js-module-blocks.
# Template Literals # Template Literals
## TemplateLiteral ## TemplateLiteral

View File

@ -56,6 +56,10 @@ import {
} from "../util/expression-scope"; } from "../util/expression-scope";
import { Errors } from "./error"; import { Errors } from "./error";
/*::
import type { SourceType } from "../options";
*/
export default class ExpressionParser extends LValParser { export default class ExpressionParser extends LValParser {
// Forward-declaration: defined in statement.js // Forward-declaration: defined in statement.js
/*:: /*::
@ -78,6 +82,16 @@ export default class ExpressionParser extends LValParser {
) => T; ) => T;
+parseFunctionParams: (node: N.Function, allowModifiers?: boolean) => void; +parseFunctionParams: (node: N.Function, allowModifiers?: boolean) => void;
+takeDecorators: (node: N.HasDecorators) => void; +takeDecorators: (node: N.HasDecorators) => void;
+parseBlockOrModuleBlockBody: (
body: N.Statement[],
directives: ?(N.Directive[]),
topLevel: boolean,
end: TokenType,
afterBlockParse?: (hasStrictModeDirective: boolean) => void
) => void
+parseProgram: (
program: N.Program, end: TokenType, sourceType?: SourceType
) => N.Program
*/ */
// For object literal, check if property __proto__ has been used more than once. // For object literal, check if property __proto__ has been used more than once.
@ -500,7 +514,13 @@ export default class ExpressionParser extends LValParser {
this.next(); this.next();
return this.parseAwait(startPos, startLoc); return this.parseAwait(startPos, startLoc);
} }
if (
this.isContextual("module") &&
this.lookaheadCharCode() === charCodes.leftCurlyBrace &&
!this.hasFollowingLineBreak()
) {
return this.parseModuleExpression();
}
const update = this.match(tt.incDec); const update = this.match(tt.incDec);
const node = this.startNode(); const node = this.startNode();
if (this.state.type.prefix) { if (this.state.type.prefix) {
@ -2630,4 +2650,24 @@ export default class ExpressionParser extends LValParser {
return ret; return ret;
} }
// https://github.com/tc39/proposal-js-module-blocks
parseModuleExpression(): N.ModuleExpression {
this.expectPlugin("moduleBlocks");
const node = this.startNode<N.ModuleExpression>();
this.next(); // eat "module"
this.eat(tt.braceL);
const revertScopes = this.initializeScopes(/** inModule */ true);
this.enterInitialScopes();
const program = this.startNode<N.Program>();
try {
node.body = this.parseProgram(program, tt.braceR, "module");
} finally {
revertScopes();
}
this.eat(tt.braceR);
return this.finishNode<N.ModuleExpression>(node, "ModuleExpression");
}
} }

View File

@ -5,14 +5,7 @@ import type { File /*::, JSXOpeningElement */ } from "../types";
import type { PluginList } from "../plugin-utils"; import type { PluginList } from "../plugin-utils";
import { getOptions } from "../options"; import { getOptions } from "../options";
import StatementParser from "./statement"; import StatementParser from "./statement";
import { SCOPE_PROGRAM } from "../util/scopeflags";
import ScopeHandler from "../util/scope"; import ScopeHandler from "../util/scope";
import ClassScopeHandler from "../util/class-scope";
import ExpressionScopeHandler from "../util/expression-scope";
import ProductionParameterHandler, {
PARAM_AWAIT,
PARAM,
} from "../util/production-parameter";
export type PluginsMap = Map<string, { [string]: any }>; export type PluginsMap = Map<string, { [string]: any }>;
@ -28,14 +21,8 @@ export default class Parser extends StatementParser {
options = getOptions(options); options = getOptions(options);
super(options, input); super(options, input);
const ScopeHandler = this.getScopeHandler();
this.options = options; this.options = options;
this.inModule = this.options.sourceType === "module"; this.initializeScopes();
this.scope = new ScopeHandler(this.raise.bind(this), this.inModule);
this.prodParam = new ProductionParameterHandler();
this.classScope = new ClassScopeHandler(this.raise.bind(this));
this.expressionScope = new ExpressionScopeHandler(this.raise.bind(this));
this.plugins = pluginsMap(this.options.plugins); this.plugins = pluginsMap(this.options.plugins);
this.filename = options.sourceFilename; this.filename = options.sourceFilename;
} }
@ -46,12 +33,7 @@ export default class Parser extends StatementParser {
} }
parse(): File { parse(): File {
let paramFlags = PARAM; this.enterInitialScopes();
if (this.hasPlugin("topLevelAwait") && this.inModule) {
paramFlags |= PARAM_AWAIT;
}
this.scope.enter(SCOPE_PROGRAM);
this.prodParam.enter(paramFlags);
const file = this.startNode(); const file = this.startNode();
const program = this.startNode(); const program = this.startNode();
this.nextToken(); this.nextToken();

View File

@ -35,6 +35,7 @@ import {
newExpressionScope, newExpressionScope,
newParameterDeclarationScope, newParameterDeclarationScope,
} from "../util/expression-scope"; } from "../util/expression-scope";
import type { SourceType } from "../options";
const loopLabel = { kind: "loop" }, const loopLabel = { kind: "loop" },
switchLabel = { kind: "switch" }; switchLabel = { kind: "switch" };
@ -55,12 +56,22 @@ export default class StatementParser extends ExpressionParser {
// to its body instead of creating a new node. // to its body instead of creating a new node.
parseTopLevel(file: N.File, program: N.Program): N.File { parseTopLevel(file: N.File, program: N.Program): N.File {
program.sourceType = this.options.sourceType; file.program = this.parseProgram(program);
file.comments = this.state.comments;
if (this.options.tokens) file.tokens = this.tokens;
return this.finishNode(file, "File");
}
parseProgram(
program: N.Program,
end: TokenType = tt.eof,
sourceType: SourceType = this.options.sourceType,
): N.Program {
program.sourceType = sourceType;
program.interpreter = this.parseInterpreterDirective(); program.interpreter = this.parseInterpreterDirective();
this.parseBlockBody(program, true, true, end);
this.parseBlockBody(program, true, true, tt.eof);
if ( if (
this.inModule && this.inModule &&
!this.options.allowUndeclaredExports && !this.options.allowUndeclaredExports &&
@ -72,13 +83,7 @@ export default class StatementParser extends ExpressionParser {
this.raise(pos, Errors.ModuleExportUndefined, name); this.raise(pos, Errors.ModuleExportUndefined, name);
} }
} }
return this.finishNode<N.Program>(program, "Program");
file.program = this.finishNode(program, "Program");
file.comments = this.state.comments;
if (this.options.tokens) file.tokens = this.tokens;
return this.finishNode(file, "File");
} }
// TODO // TODO

View File

@ -6,7 +6,17 @@ import State from "../tokenizer/state";
import type { Node } from "../types"; import type { Node } from "../types";
import { lineBreak } from "../util/whitespace"; import { lineBreak } from "../util/whitespace";
import { isIdentifierChar } from "../util/identifier"; import { isIdentifierChar } from "../util/identifier";
import ClassScopeHandler from "../util/class-scope";
import ExpressionScopeHandler from "../util/expression-scope";
import { SCOPE_PROGRAM } from "../util/scopeflags";
import ProductionParameterHandler, {
PARAM_AWAIT,
PARAM,
} from "../util/production-parameter";
import { Errors } from "./error"; import { Errors } from "./error";
/*::
import type ScopeHandler from "../util/scope";
*/
type TryParse<Node, Error, Thrown, Aborted, FailState> = { type TryParse<Node, Error, Thrown, Aborted, FailState> = {
node: Node, node: Node,
@ -19,6 +29,11 @@ type TryParse<Node, Error, Thrown, Aborted, FailState> = {
// ## Parser utilities // ## Parser utilities
export default class UtilParser extends Tokenizer { export default class UtilParser extends Tokenizer {
// Forward-declaration: defined in parser/index.js
/*::
+getScopeHandler: () => Class<ScopeHandler<*>>;
*/
// TODO // TODO
addExtra(node: Node, key: string, val: any): void { addExtra(node: Node, key: string, val: any): void {
@ -304,6 +319,56 @@ export default class UtilParser extends Tokenizer {
isObjectMethod(node: Node): boolean { isObjectMethod(node: Node): boolean {
return node.type === "ObjectMethod"; return node.type === "ObjectMethod";
} }
initializeScopes(
inModule: boolean = this.options.sourceType === "module",
): () => void {
// Initialize state
const oldLabels = this.state.labels;
this.state.labels = [];
const oldExportedIdentifiers = this.state.exportedIdentifiers;
this.state.exportedIdentifiers = [];
// initialize scopes
const oldInModule = this.inModule;
this.inModule = inModule;
const oldScope = this.scope;
const ScopeHandler = this.getScopeHandler();
this.scope = new ScopeHandler(this.raise.bind(this), this.inModule);
const oldProdParam = this.prodParam;
this.prodParam = new ProductionParameterHandler();
const oldClassScope = this.classScope;
this.classScope = new ClassScopeHandler(this.raise.bind(this));
const oldExpressionScope = this.expressionScope;
this.expressionScope = new ExpressionScopeHandler(this.raise.bind(this));
return () => {
// Revert state
this.state.labels = oldLabels;
this.state.exportedIdentifiers = oldExportedIdentifiers;
// Revert scopes
this.inModule = oldInModule;
this.scope = oldScope;
this.prodParam = oldProdParam;
this.classScope = oldClassScope;
this.expressionScope = oldExpressionScope;
};
}
enterInitialScopes() {
let paramFlags = PARAM;
if (this.hasPlugin("topLevelAwait") && this.inModule) {
paramFlags |= PARAM_AWAIT;
}
this.scope.enter(SCOPE_PROGRAM);
this.prodParam.enter(paramFlags);
}
} }
/** /**

View File

@ -655,6 +655,11 @@ export type TemplateElement = NodeBase & {
}, },
}; };
export type ModuleExpression = NodeBase & {
type: "ModuleExpression",
body: Program,
};
// Patterns // Patterns
// TypeScript access modifiers // TypeScript access modifiers

View File

@ -0,0 +1,4 @@
{
"sourceType": "script",
"plugins": ["moduleBlocks"]
}

View File

@ -0,0 +1,55 @@
{
"type": "File",
"start":0,"end":20,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":20}},
"errors": [
"SyntaxError: Unexpected reserved word 'await' (1:9)"
],
"program": {
"type": "Program",
"start":0,"end":20,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":20}},
"sourceType": "script",
"interpreter": null,
"body": [
{
"type": "ExpressionStatement",
"start":0,"end":20,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":20}},
"expression": {
"type": "ModuleExpression",
"start":0,"end":19,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":19}},
"body": {
"type": "Program",
"start":9,"end":19,"loc":{"start":{"line":1,"column":9},"end":{"line":1,"column":19}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "LabeledStatement",
"start":9,"end":17,"loc":{"start":{"line":1,"column":9},"end":{"line":1,"column":17}},
"body": {
"type": "ExpressionStatement",
"start":16,"end":17,"loc":{"start":{"line":1,"column":16},"end":{"line":1,"column":17}},
"expression": {
"type": "NumericLiteral",
"start":16,"end":17,"loc":{"start":{"line":1,"column":16},"end":{"line":1,"column":17}},
"extra": {
"rawValue": 3,
"raw": "3"
},
"value": 3
}
},
"label": {
"type": "Identifier",
"start":9,"end":14,"loc":{"start":{"line":1,"column":9},"end":{"line":1,"column":14},"identifierName":"await"},
"name": "await"
}
}
],
"directives": []
}
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,7 @@
class B {
#p() {
module {
class C { [this.#p]; }
};
}
}

View File

@ -0,0 +1,9 @@
{
"sourceType": "module",
"plugins": [
"moduleBlocks",
"classPrivateProperties",
"classPrivateMethods",
"classProperties"
]
}

View File

@ -0,0 +1,116 @@
{
"type": "File",
"start":0,"end":73,"loc":{"start":{"line":1,"column":0},"end":{"line":7,"column":1}},
"errors": [
"SyntaxError: Private name #p is not defined (4:22)"
],
"program": {
"type": "Program",
"start":0,"end":73,"loc":{"start":{"line":1,"column":0},"end":{"line":7,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ClassDeclaration",
"start":0,"end":73,"loc":{"start":{"line":1,"column":0},"end":{"line":7,"column":1}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"B"},
"name": "B"
},
"superClass": null,
"body": {
"type": "ClassBody",
"start":8,"end":73,"loc":{"start":{"line":1,"column":8},"end":{"line":7,"column":1}},
"body": [
{
"type": "ClassPrivateMethod",
"start":12,"end":71,"loc":{"start":{"line":2,"column":2},"end":{"line":6,"column":3}},
"static": false,
"key": {
"type": "PrivateName",
"start":12,"end":14,"loc":{"start":{"line":2,"column":2},"end":{"line":2,"column":4}},
"id": {
"type": "Identifier",
"start":13,"end":14,"loc":{"start":{"line":2,"column":3},"end":{"line":2,"column":4},"identifierName":"p"},
"name": "p"
}
},
"kind": "method",
"id": null,
"generator": false,
"async": false,
"params": [],
"body": {
"type": "BlockStatement",
"start":17,"end":71,"loc":{"start":{"line":2,"column":7},"end":{"line":6,"column":3}},
"body": [
{
"type": "ExpressionStatement",
"start":23,"end":67,"loc":{"start":{"line":3,"column":4},"end":{"line":5,"column":6}},
"expression": {
"type": "ModuleExpression",
"start":23,"end":66,"loc":{"start":{"line":3,"column":4},"end":{"line":5,"column":5}},
"body": {
"type": "Program",
"start":38,"end":66,"loc":{"start":{"line":4,"column":6},"end":{"line":5,"column":5}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ClassDeclaration",
"start":38,"end":60,"loc":{"start":{"line":4,"column":6},"end":{"line":4,"column":28}},
"id": {
"type": "Identifier",
"start":44,"end":45,"loc":{"start":{"line":4,"column":12},"end":{"line":4,"column":13},"identifierName":"C"},
"name": "C"
},
"superClass": null,
"body": {
"type": "ClassBody",
"start":46,"end":60,"loc":{"start":{"line":4,"column":14},"end":{"line":4,"column":28}},
"body": [
{
"type": "ClassProperty",
"start":48,"end":58,"loc":{"start":{"line":4,"column":16},"end":{"line":4,"column":26}},
"static": false,
"computed": true,
"key": {
"type": "MemberExpression",
"start":49,"end":56,"loc":{"start":{"line":4,"column":17},"end":{"line":4,"column":24}},
"object": {
"type": "ThisExpression",
"start":49,"end":53,"loc":{"start":{"line":4,"column":17},"end":{"line":4,"column":21}}
},
"computed": false,
"property": {
"type": "PrivateName",
"start":54,"end":56,"loc":{"start":{"line":4,"column":22},"end":{"line":4,"column":24}},
"id": {
"type": "Identifier",
"start":55,"end":56,"loc":{"start":{"line":4,"column":23},"end":{"line":4,"column":24},"identifierName":"p"},
"name": "p"
}
}
},
"value": null
}
]
}
}
],
"directives": []
}
}
}
],
"directives": []
}
}
]
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,4 @@
const m = module {
export const foo = "foo";
export { foo };
};

View File

@ -0,0 +1,98 @@
{
"type": "File",
"start":0,"end":67,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":2}},
"errors": [
"SyntaxError: `foo` has already been exported. Exported identifiers must be unique. (3:11)"
],
"program": {
"type": "Program",
"start":0,"end":67,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":2}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":67,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":2}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":66,"loc":{"start":{"line":1,"column":6},"end":{"line":4,"column":1}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "ModuleExpression",
"start":10,"end":66,"loc":{"start":{"line":1,"column":10},"end":{"line":4,"column":1}},
"body": {
"type": "Program",
"start":21,"end":66,"loc":{"start":{"line":2,"column":2},"end":{"line":4,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":21,"end":46,"loc":{"start":{"line":2,"column":2},"end":{"line":2,"column":27}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":28,"end":46,"loc":{"start":{"line":2,"column":9},"end":{"line":2,"column":27}},
"declarations": [
{
"type": "VariableDeclarator",
"start":34,"end":45,"loc":{"start":{"line":2,"column":15},"end":{"line":2,"column":26}},
"id": {
"type": "Identifier",
"start":34,"end":37,"loc":{"start":{"line":2,"column":15},"end":{"line":2,"column":18},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":40,"end":45,"loc":{"start":{"line":2,"column":21},"end":{"line":2,"column":26}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
},
{
"type": "ExportNamedDeclaration",
"start":49,"end":64,"loc":{"start":{"line":3,"column":2},"end":{"line":3,"column":17}},
"specifiers": [
{
"type": "ExportSpecifier",
"start":58,"end":61,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":14}},
"local": {
"type": "Identifier",
"start":58,"end":61,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":14},"identifierName":"foo"},
"name": "foo"
},
"exported": {
"type": "Identifier",
"start":58,"end":61,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":14},"identifierName":"foo"},
"name": "foo"
}
}
],
"source": null,
"declaration": null
}
],
"directives": []
}
}
}
],
"kind": "const"
}
],
"directives": []
}
}

View File

@ -0,0 +1,40 @@
{
"type": "File",
"start":0,"end":19,"loc":{"start":{"line":1,"column":0},"end":{"line":2,"column":2}},
"program": {
"type": "Program",
"start":0,"end":19,"loc":{"start":{"line":1,"column":0},"end":{"line":2,"column":2}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":16,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":16}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":16,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":16}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "Identifier",
"start":10,"end":16,"loc":{"start":{"line":1,"column":10},"end":{"line":1,"column":16},"identifierName":"module"},
"name": "module"
}
}
],
"kind": "const"
},
{
"type": "BlockStatement",
"start":17,"end":19,"loc":{"start":{"line":2,"column":0},"end":{"line":2,"column":2}},
"body": [],
"directives": []
}
],
"directives": []
}
}

View File

@ -0,0 +1,3 @@
module {
export { foo }
}

View File

@ -0,0 +1,55 @@
{
"type": "File",
"start":0,"end":27,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":1}},
"errors": [
"SyntaxError: Export 'foo' is not defined (2:11)"
],
"program": {
"type": "Program",
"start":0,"end":27,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExpressionStatement",
"start":0,"end":27,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":1}},
"expression": {
"type": "ModuleExpression",
"start":0,"end":27,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":1}},
"body": {
"type": "Program",
"start":11,"end":27,"loc":{"start":{"line":2,"column":2},"end":{"line":3,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":11,"end":25,"loc":{"start":{"line":2,"column":2},"end":{"line":2,"column":16}},
"specifiers": [
{
"type": "ExportSpecifier",
"start":20,"end":23,"loc":{"start":{"line":2,"column":11},"end":{"line":2,"column":14}},
"local": {
"type": "Identifier",
"start":20,"end":23,"loc":{"start":{"line":2,"column":11},"end":{"line":2,"column":14},"identifierName":"foo"},
"name": "foo"
},
"exported": {
"type": "Identifier",
"start":20,"end":23,"loc":{"start":{"line":2,"column":11},"end":{"line":2,"column":14},"identifierName":"foo"},
"name": "foo"
}
}
],
"source": null,
"declaration": null
}
],
"directives": []
}
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,4 @@
let foo;
module {
export { foo };
}

View File

@ -0,0 +1,72 @@
{
"type": "File",
"start":0,"end":37,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":1}},
"errors": [
"SyntaxError: Export 'foo' is not defined (3:11)"
],
"program": {
"type": "Program",
"start":0,"end":37,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":8,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":8}},
"declarations": [
{
"type": "VariableDeclarator",
"start":4,"end":7,"loc":{"start":{"line":1,"column":4},"end":{"line":1,"column":7}},
"id": {
"type": "Identifier",
"start":4,"end":7,"loc":{"start":{"line":1,"column":4},"end":{"line":1,"column":7},"identifierName":"foo"},
"name": "foo"
},
"init": null
}
],
"kind": "let"
},
{
"type": "ExpressionStatement",
"start":9,"end":37,"loc":{"start":{"line":2,"column":0},"end":{"line":4,"column":1}},
"expression": {
"type": "ModuleExpression",
"start":9,"end":37,"loc":{"start":{"line":2,"column":0},"end":{"line":4,"column":1}},
"body": {
"type": "Program",
"start":20,"end":37,"loc":{"start":{"line":3,"column":2},"end":{"line":4,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":20,"end":35,"loc":{"start":{"line":3,"column":2},"end":{"line":3,"column":17}},
"specifiers": [
{
"type": "ExportSpecifier",
"start":29,"end":32,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":14}},
"local": {
"type": "Identifier",
"start":29,"end":32,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":14},"identifierName":"foo"},
"name": "foo"
},
"exported": {
"type": "Identifier",
"start":29,"end":32,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":14},"identifierName":"foo"},
"name": "foo"
}
}
],
"source": null,
"declaration": null
}
],
"directives": []
}
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,4 @@
{
"sourceType": "module",
"plugins": ["moduleBlocks"]
}

View File

@ -0,0 +1,3 @@
const m = module {
export const foo = "foo";
};

View File

@ -0,0 +1,73 @@
{
"type": "File",
"start":0,"end":49,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":2}},
"program": {
"type": "Program",
"start":0,"end":49,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":2}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":49,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":2}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":48,"loc":{"start":{"line":1,"column":6},"end":{"line":3,"column":1}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "ModuleExpression",
"start":10,"end":48,"loc":{"start":{"line":1,"column":10},"end":{"line":3,"column":1}},
"body": {
"type": "Program",
"start":21,"end":48,"loc":{"start":{"line":2,"column":2},"end":{"line":3,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":21,"end":46,"loc":{"start":{"line":2,"column":2},"end":{"line":2,"column":27}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":28,"end":46,"loc":{"start":{"line":2,"column":9},"end":{"line":2,"column":27}},
"declarations": [
{
"type": "VariableDeclarator",
"start":34,"end":45,"loc":{"start":{"line":2,"column":15},"end":{"line":2,"column":26}},
"id": {
"type": "Identifier",
"start":34,"end":37,"loc":{"start":{"line":2,"column":15},"end":{"line":2,"column":18},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":40,"end":45,"loc":{"start":{"line":2,"column":21},"end":{"line":2,"column":26}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
}
],
"directives": []
}
}
}
],
"kind": "const"
}
],
"directives": []
}
}

View File

@ -0,0 +1,11 @@
class B {
#p() {
module {
class C {
[this.#p];
#p = 3;
}
};
}
}

View File

@ -0,0 +1,9 @@
{
"sourceType": "module",
"plugins": [
"moduleBlocks",
"classPrivateProperties",
"classPrivateMethods",
"classProperties"
]
}

View File

@ -0,0 +1,136 @@
{
"type": "File",
"start":0,"end":103,"loc":{"start":{"line":1,"column":0},"end":{"line":10,"column":1}},
"program": {
"type": "Program",
"start":0,"end":103,"loc":{"start":{"line":1,"column":0},"end":{"line":10,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ClassDeclaration",
"start":0,"end":103,"loc":{"start":{"line":1,"column":0},"end":{"line":10,"column":1}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"B"},
"name": "B"
},
"superClass": null,
"body": {
"type": "ClassBody",
"start":8,"end":103,"loc":{"start":{"line":1,"column":8},"end":{"line":10,"column":1}},
"body": [
{
"type": "ClassPrivateMethod",
"start":12,"end":101,"loc":{"start":{"line":2,"column":2},"end":{"line":9,"column":3}},
"static": false,
"key": {
"type": "PrivateName",
"start":12,"end":14,"loc":{"start":{"line":2,"column":2},"end":{"line":2,"column":4}},
"id": {
"type": "Identifier",
"start":13,"end":14,"loc":{"start":{"line":2,"column":3},"end":{"line":2,"column":4},"identifierName":"p"},
"name": "p"
}
},
"kind": "method",
"id": null,
"generator": false,
"async": false,
"params": [],
"body": {
"type": "BlockStatement",
"start":17,"end":101,"loc":{"start":{"line":2,"column":7},"end":{"line":9,"column":3}},
"body": [
{
"type": "ExpressionStatement",
"start":23,"end":97,"loc":{"start":{"line":3,"column":4},"end":{"line":8,"column":6}},
"expression": {
"type": "ModuleExpression",
"start":23,"end":96,"loc":{"start":{"line":3,"column":4},"end":{"line":8,"column":5}},
"body": {
"type": "Program",
"start":38,"end":96,"loc":{"start":{"line":4,"column":6},"end":{"line":8,"column":5}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ClassDeclaration",
"start":38,"end":90,"loc":{"start":{"line":4,"column":6},"end":{"line":7,"column":7}},
"id": {
"type": "Identifier",
"start":44,"end":45,"loc":{"start":{"line":4,"column":12},"end":{"line":4,"column":13},"identifierName":"C"},
"name": "C"
},
"superClass": null,
"body": {
"type": "ClassBody",
"start":46,"end":90,"loc":{"start":{"line":4,"column":14},"end":{"line":7,"column":7}},
"body": [
{
"type": "ClassProperty",
"start":56,"end":66,"loc":{"start":{"line":5,"column":8},"end":{"line":5,"column":18}},
"static": false,
"computed": true,
"key": {
"type": "MemberExpression",
"start":57,"end":64,"loc":{"start":{"line":5,"column":9},"end":{"line":5,"column":16}},
"object": {
"type": "ThisExpression",
"start":57,"end":61,"loc":{"start":{"line":5,"column":9},"end":{"line":5,"column":13}}
},
"computed": false,
"property": {
"type": "PrivateName",
"start":62,"end":64,"loc":{"start":{"line":5,"column":14},"end":{"line":5,"column":16}},
"id": {
"type": "Identifier",
"start":63,"end":64,"loc":{"start":{"line":5,"column":15},"end":{"line":5,"column":16},"identifierName":"p"},
"name": "p"
}
}
},
"value": null
},
{
"type": "ClassPrivateProperty",
"start":75,"end":82,"loc":{"start":{"line":6,"column":8},"end":{"line":6,"column":15}},
"static": false,
"key": {
"type": "PrivateName",
"start":75,"end":77,"loc":{"start":{"line":6,"column":8},"end":{"line":6,"column":10}},
"id": {
"type": "Identifier",
"start":76,"end":77,"loc":{"start":{"line":6,"column":9},"end":{"line":6,"column":10},"identifierName":"p"},
"name": "p"
}
},
"value": {
"type": "NumericLiteral",
"start":80,"end":81,"loc":{"start":{"line":6,"column":13},"end":{"line":6,"column":14}},
"extra": {
"rawValue": 3,
"raw": "3"
},
"value": 3
}
}
]
}
}
],
"directives": []
}
}
}
],
"directives": []
}
}
]
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,3 @@
export const foo = "foo";
const m1 = module { export const foo = "foo" };
const m2 = module { export const foo = "foo" };

View File

@ -0,0 +1,164 @@
{
"type": "File",
"start":0,"end":121,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":47}},
"program": {
"type": "Program",
"start":0,"end":121,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":47}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":0,"end":25,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":25}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":7,"end":25,"loc":{"start":{"line":1,"column":7},"end":{"line":1,"column":25}},
"declarations": [
{
"type": "VariableDeclarator",
"start":13,"end":24,"loc":{"start":{"line":1,"column":13},"end":{"line":1,"column":24}},
"id": {
"type": "Identifier",
"start":13,"end":16,"loc":{"start":{"line":1,"column":13},"end":{"line":1,"column":16},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":19,"end":24,"loc":{"start":{"line":1,"column":19},"end":{"line":1,"column":24}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
},
{
"type": "VariableDeclaration",
"start":26,"end":73,"loc":{"start":{"line":2,"column":0},"end":{"line":2,"column":47}},
"declarations": [
{
"type": "VariableDeclarator",
"start":32,"end":72,"loc":{"start":{"line":2,"column":6},"end":{"line":2,"column":46}},
"id": {
"type": "Identifier",
"start":32,"end":34,"loc":{"start":{"line":2,"column":6},"end":{"line":2,"column":8},"identifierName":"m1"},
"name": "m1"
},
"init": {
"type": "ModuleExpression",
"start":37,"end":72,"loc":{"start":{"line":2,"column":11},"end":{"line":2,"column":46}},
"body": {
"type": "Program",
"start":46,"end":72,"loc":{"start":{"line":2,"column":20},"end":{"line":2,"column":46}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":46,"end":70,"loc":{"start":{"line":2,"column":20},"end":{"line":2,"column":44}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":53,"end":70,"loc":{"start":{"line":2,"column":27},"end":{"line":2,"column":44}},
"declarations": [
{
"type": "VariableDeclarator",
"start":59,"end":70,"loc":{"start":{"line":2,"column":33},"end":{"line":2,"column":44}},
"id": {
"type": "Identifier",
"start":59,"end":62,"loc":{"start":{"line":2,"column":33},"end":{"line":2,"column":36},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":65,"end":70,"loc":{"start":{"line":2,"column":39},"end":{"line":2,"column":44}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
}
],
"directives": []
}
}
}
],
"kind": "const"
},
{
"type": "VariableDeclaration",
"start":74,"end":121,"loc":{"start":{"line":3,"column":0},"end":{"line":3,"column":47}},
"declarations": [
{
"type": "VariableDeclarator",
"start":80,"end":120,"loc":{"start":{"line":3,"column":6},"end":{"line":3,"column":46}},
"id": {
"type": "Identifier",
"start":80,"end":82,"loc":{"start":{"line":3,"column":6},"end":{"line":3,"column":8},"identifierName":"m2"},
"name": "m2"
},
"init": {
"type": "ModuleExpression",
"start":85,"end":120,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":46}},
"body": {
"type": "Program",
"start":94,"end":120,"loc":{"start":{"line":3,"column":20},"end":{"line":3,"column":46}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":94,"end":118,"loc":{"start":{"line":3,"column":20},"end":{"line":3,"column":44}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":101,"end":118,"loc":{"start":{"line":3,"column":27},"end":{"line":3,"column":44}},
"declarations": [
{
"type": "VariableDeclarator",
"start":107,"end":118,"loc":{"start":{"line":3,"column":33},"end":{"line":3,"column":44}},
"id": {
"type": "Identifier",
"start":107,"end":110,"loc":{"start":{"line":3,"column":33},"end":{"line":3,"column":36},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":113,"end":118,"loc":{"start":{"line":3,"column":39},"end":{"line":3,"column":44}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
}
],
"directives": []
}
}
}
],
"kind": "const"
}
],
"directives": []
}
}

View File

@ -0,0 +1,4 @@
const foo = "foo";
const m = module {
const foo = "foo";
};

View File

@ -0,0 +1,92 @@
{
"type": "File",
"start":0,"end":61,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":2}},
"program": {
"type": "Program",
"start":0,"end":61,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":2}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":18,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":18}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":17,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":17}},
"id": {
"type": "Identifier",
"start":6,"end":9,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":9},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":12,"end":17,"loc":{"start":{"line":1,"column":12},"end":{"line":1,"column":17}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
},
{
"type": "VariableDeclaration",
"start":19,"end":61,"loc":{"start":{"line":2,"column":0},"end":{"line":4,"column":2}},
"declarations": [
{
"type": "VariableDeclarator",
"start":25,"end":60,"loc":{"start":{"line":2,"column":6},"end":{"line":4,"column":1}},
"id": {
"type": "Identifier",
"start":25,"end":26,"loc":{"start":{"line":2,"column":6},"end":{"line":2,"column":7},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "ModuleExpression",
"start":29,"end":60,"loc":{"start":{"line":2,"column":10},"end":{"line":4,"column":1}},
"body": {
"type": "Program",
"start":40,"end":60,"loc":{"start":{"line":3,"column":2},"end":{"line":4,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":40,"end":58,"loc":{"start":{"line":3,"column":2},"end":{"line":3,"column":20}},
"declarations": [
{
"type": "VariableDeclarator",
"start":46,"end":57,"loc":{"start":{"line":3,"column":8},"end":{"line":3,"column":19}},
"id": {
"type": "Identifier",
"start":46,"end":49,"loc":{"start":{"line":3,"column":8},"end":{"line":3,"column":11},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":52,"end":57,"loc":{"start":{"line":3,"column":14},"end":{"line":3,"column":19}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
],
"directives": []
}
}
}
],
"kind": "const"
}
],
"directives": []
}
}

View File

@ -0,0 +1,29 @@
{
"type": "File",
"start":0,"end":10,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":10}},
"program": {
"type": "Program",
"start":0,"end":10,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":10}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExpressionStatement",
"start":0,"end":10,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":10}},
"expression": {
"type": "ModuleExpression",
"start":0,"end":9,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":9}},
"body": {
"type": "Program",
"start":8,"end":9,"loc":{"start":{"line":1,"column":8},"end":{"line":1,"column":9}},
"sourceType": "module",
"interpreter": null,
"body": [],
"directives": []
}
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,4 @@
const m = module {
export const foo = "foo";
};
import(module);

View File

@ -0,0 +1,92 @@
{
"type": "File",
"start":0,"end":65,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":15}},
"program": {
"type": "Program",
"start":0,"end":65,"loc":{"start":{"line":1,"column":0},"end":{"line":4,"column":15}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":49,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":2}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":48,"loc":{"start":{"line":1,"column":6},"end":{"line":3,"column":1}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "ModuleExpression",
"start":10,"end":48,"loc":{"start":{"line":1,"column":10},"end":{"line":3,"column":1}},
"body": {
"type": "Program",
"start":21,"end":48,"loc":{"start":{"line":2,"column":2},"end":{"line":3,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":21,"end":46,"loc":{"start":{"line":2,"column":2},"end":{"line":2,"column":27}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":28,"end":46,"loc":{"start":{"line":2,"column":9},"end":{"line":2,"column":27}},
"declarations": [
{
"type": "VariableDeclarator",
"start":34,"end":45,"loc":{"start":{"line":2,"column":15},"end":{"line":2,"column":26}},
"id": {
"type": "Identifier",
"start":34,"end":37,"loc":{"start":{"line":2,"column":15},"end":{"line":2,"column":18},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":40,"end":45,"loc":{"start":{"line":2,"column":21},"end":{"line":2,"column":26}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
}
],
"directives": []
}
}
}
],
"kind": "const"
},
{
"type": "ExpressionStatement",
"start":50,"end":65,"loc":{"start":{"line":4,"column":0},"end":{"line":4,"column":15}},
"expression": {
"type": "CallExpression",
"start":50,"end":64,"loc":{"start":{"line":4,"column":0},"end":{"line":4,"column":14}},
"callee": {
"type": "Import",
"start":50,"end":56,"loc":{"start":{"line":4,"column":0},"end":{"line":4,"column":6}}
},
"arguments": [
{
"type": "Identifier",
"start":57,"end":63,"loc":{"start":{"line":4,"column":7},"end":{"line":4,"column":13},"identifierName":"module"},
"name": "module"
}
]
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,3 @@
const worker = new Worker(module {
export const foo = "foo";
});

View File

@ -0,0 +1,84 @@
{
"type": "File",
"start":0,"end":68,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":3}},
"program": {
"type": "Program",
"start":0,"end":68,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":3}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":68,"loc":{"start":{"line":1,"column":0},"end":{"line":3,"column":3}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":67,"loc":{"start":{"line":1,"column":6},"end":{"line":3,"column":2}},
"id": {
"type": "Identifier",
"start":6,"end":12,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":12},"identifierName":"worker"},
"name": "worker"
},
"init": {
"type": "NewExpression",
"start":15,"end":67,"loc":{"start":{"line":1,"column":15},"end":{"line":3,"column":2}},
"callee": {
"type": "Identifier",
"start":19,"end":25,"loc":{"start":{"line":1,"column":19},"end":{"line":1,"column":25},"identifierName":"Worker"},
"name": "Worker"
},
"arguments": [
{
"type": "ModuleExpression",
"start":26,"end":66,"loc":{"start":{"line":1,"column":26},"end":{"line":3,"column":1}},
"body": {
"type": "Program",
"start":39,"end":66,"loc":{"start":{"line":2,"column":4},"end":{"line":3,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":39,"end":64,"loc":{"start":{"line":2,"column":4},"end":{"line":2,"column":29}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":46,"end":64,"loc":{"start":{"line":2,"column":11},"end":{"line":2,"column":29}},
"declarations": [
{
"type": "VariableDeclarator",
"start":52,"end":63,"loc":{"start":{"line":2,"column":17},"end":{"line":2,"column":28}},
"id": {
"type": "Identifier",
"start":52,"end":55,"loc":{"start":{"line":2,"column":17},"end":{"line":2,"column":20},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":58,"end":63,"loc":{"start":{"line":2,"column":23},"end":{"line":2,"column":28}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
}
],
"directives": []
}
}
]
}
}
],
"kind": "const"
}
],
"directives": []
}
}

View File

@ -0,0 +1,5 @@
let m = module {
module {
export let foo = "foo";
};
};

View File

@ -0,0 +1,90 @@
{
"type": "File",
"start":0,"end":63,"loc":{"start":{"line":1,"column":0},"end":{"line":5,"column":2}},
"program": {
"type": "Program",
"start":0,"end":63,"loc":{"start":{"line":1,"column":0},"end":{"line":5,"column":2}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":63,"loc":{"start":{"line":1,"column":0},"end":{"line":5,"column":2}},
"declarations": [
{
"type": "VariableDeclarator",
"start":4,"end":62,"loc":{"start":{"line":1,"column":4},"end":{"line":5,"column":1}},
"id": {
"type": "Identifier",
"start":4,"end":5,"loc":{"start":{"line":1,"column":4},"end":{"line":1,"column":5},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "ModuleExpression",
"start":8,"end":62,"loc":{"start":{"line":1,"column":8},"end":{"line":5,"column":1}},
"body": {
"type": "Program",
"start":19,"end":62,"loc":{"start":{"line":2,"column":2},"end":{"line":5,"column":1}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExpressionStatement",
"start":19,"end":60,"loc":{"start":{"line":2,"column":2},"end":{"line":4,"column":4}},
"expression": {
"type": "ModuleExpression",
"start":19,"end":59,"loc":{"start":{"line":2,"column":2},"end":{"line":4,"column":3}},
"body": {
"type": "Program",
"start":32,"end":59,"loc":{"start":{"line":3,"column":4},"end":{"line":4,"column":3}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":32,"end":55,"loc":{"start":{"line":3,"column":4},"end":{"line":3,"column":27}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":39,"end":55,"loc":{"start":{"line":3,"column":11},"end":{"line":3,"column":27}},
"declarations": [
{
"type": "VariableDeclarator",
"start":43,"end":54,"loc":{"start":{"line":3,"column":15},"end":{"line":3,"column":26}},
"id": {
"type": "Identifier",
"start":43,"end":46,"loc":{"start":{"line":3,"column":15},"end":{"line":3,"column":18},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":49,"end":54,"loc":{"start":{"line":3,"column":21},"end":{"line":3,"column":26}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "let"
}
}
],
"directives": []
}
}
}
],
"directives": []
}
}
}
],
"kind": "let"
}
],
"directives": []
}
}

View File

@ -0,0 +1 @@
const m = module { export const foo = "foo" };

View File

@ -0,0 +1,73 @@
{
"type": "File",
"start":0,"end":46,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":46}},
"program": {
"type": "Program",
"start":0,"end":46,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":46}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "VariableDeclaration",
"start":0,"end":46,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":46}},
"declarations": [
{
"type": "VariableDeclarator",
"start":6,"end":45,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":45}},
"id": {
"type": "Identifier",
"start":6,"end":7,"loc":{"start":{"line":1,"column":6},"end":{"line":1,"column":7},"identifierName":"m"},
"name": "m"
},
"init": {
"type": "ModuleExpression",
"start":10,"end":45,"loc":{"start":{"line":1,"column":10},"end":{"line":1,"column":45}},
"body": {
"type": "Program",
"start":19,"end":45,"loc":{"start":{"line":1,"column":19},"end":{"line":1,"column":45}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExportNamedDeclaration",
"start":19,"end":43,"loc":{"start":{"line":1,"column":19},"end":{"line":1,"column":43}},
"specifiers": [],
"source": null,
"declaration": {
"type": "VariableDeclaration",
"start":26,"end":43,"loc":{"start":{"line":1,"column":26},"end":{"line":1,"column":43}},
"declarations": [
{
"type": "VariableDeclarator",
"start":32,"end":43,"loc":{"start":{"line":1,"column":32},"end":{"line":1,"column":43}},
"id": {
"type": "Identifier",
"start":32,"end":35,"loc":{"start":{"line":1,"column":32},"end":{"line":1,"column":35},"identifierName":"foo"},
"name": "foo"
},
"init": {
"type": "StringLiteral",
"start":38,"end":43,"loc":{"start":{"line":1,"column":38},"end":{"line":1,"column":43}},
"extra": {
"rawValue": "foo",
"raw": "\"foo\""
},
"value": "foo"
}
}
],
"kind": "const"
}
}
],
"directives": []
}
}
}
],
"kind": "const"
}
],
"directives": []
}
}

View File

@ -0,0 +1,4 @@
{
"sourceType": "module",
"plugins": ["moduleBlocks", "topLevelAwait"]
}

View File

@ -0,0 +1,47 @@
{
"type": "File",
"start":0,"end":19,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":19}},
"program": {
"type": "Program",
"start":0,"end":19,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":19}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExpressionStatement",
"start":0,"end":19,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":19}},
"expression": {
"type": "ModuleExpression",
"start":0,"end":18,"loc":{"start":{"line":1,"column":0},"end":{"line":1,"column":18}},
"body": {
"type": "Program",
"start":9,"end":18,"loc":{"start":{"line":1,"column":9},"end":{"line":1,"column":18}},
"sourceType": "module",
"interpreter": null,
"body": [
{
"type": "ExpressionStatement",
"start":9,"end":16,"loc":{"start":{"line":1,"column":9},"end":{"line":1,"column":16}},
"expression": {
"type": "AwaitExpression",
"start":9,"end":16,"loc":{"start":{"line":1,"column":9},"end":{"line":1,"column":16}},
"argument": {
"type": "NumericLiteral",
"start":15,"end":16,"loc":{"start":{"line":1,"column":15},"end":{"line":1,"column":16}},
"extra": {
"rawValue": 3,
"raw": "3"
},
"value": 3
}
}
}
],
"directives": []
}
}
}
],
"directives": []
}
}

View File

@ -0,0 +1,3 @@
src
test
*.log

View File

@ -0,0 +1,19 @@
# @babel/plugin-syntax-module-blocks
> Allow parsing of module blocks
See our website [@babel/plugin-syntax-module-blocks](https://babeljs.io/docs/en/babel-plugin-syntax-module-blocks) for more information.
## Install
Using npm:
```sh
npm install --save-dev @babel/plugin-syntax-module-blocks
```
or using yarn:
```sh
yarn add @babel/plugin-syntax-module-blocks --dev
```

View File

@ -0,0 +1,27 @@
{
"name": "@babel/plugin-syntax-module-blocks",
"version": "7.11.0",
"description": "Allow parsing of JS Module Blocks",
"repository": {
"type": "git",
"url": "https://github.com/babel/babel.git",
"directory": "packages/babel-plugin-syntax-module-blocks"
},
"license": "MIT",
"publishConfig": {
"access": "public"
},
"main": "lib/index.js",
"exports": {
".": "./lib/index.js"
},
"keywords": [
"babel-plugin"
],
"dependencies": {
"@babel/helper-plugin-utils": "workspace:^7.10.1"
},
"peerDependencies": {
"@babel/core": "^7.0.0-0"
}
}

View File

@ -0,0 +1,13 @@
import { declare } from "@babel/helper-plugin-utils";
export default declare(api => {
api.assertVersion(7);
return {
name: "syntax-module-blocks",
manipulateOptions(opts, parserOpts) {
parserOpts.plugins.push("moduleBlocks");
},
};
});

View File

@ -45,6 +45,7 @@
"@babel/plugin-syntax-import-assertions": "workspace:*", "@babel/plugin-syntax-import-assertions": "workspace:*",
"@babel/plugin-syntax-import-meta": "^7.10.4", "@babel/plugin-syntax-import-meta": "^7.10.4",
"@babel/plugin-syntax-jsx": "workspace:*", "@babel/plugin-syntax-jsx": "workspace:*",
"@babel/plugin-syntax-module-blocks": "workspace:*",
"@babel/plugin-syntax-object-rest-spread": "^7.8.0", "@babel/plugin-syntax-object-rest-spread": "^7.8.0",
"@babel/plugin-syntax-optional-catch-binding": "^7.8.0", "@babel/plugin-syntax-optional-catch-binding": "^7.8.0",
"@babel/plugin-syntax-pipeline-operator": "workspace:*", "@babel/plugin-syntax-pipeline-operator": "workspace:*",

View File

@ -10,6 +10,7 @@
"syntax-flow", "syntax-flow",
"syntax-function-bind", "syntax-function-bind",
"syntax-function-sent", "syntax-function-sent",
"syntax-module-blocks",
"syntax-import-meta", "syntax-import-meta",
"syntax-jsx", "syntax-jsx",
"syntax-import-assertions", "syntax-import-assertions",

View File

@ -13,6 +13,7 @@ import syntaxExportDefaultFrom from "@babel/plugin-syntax-export-default-from";
import syntaxFlow from "@babel/plugin-syntax-flow"; import syntaxFlow from "@babel/plugin-syntax-flow";
import syntaxFunctionBind from "@babel/plugin-syntax-function-bind"; import syntaxFunctionBind from "@babel/plugin-syntax-function-bind";
import syntaxFunctionSent from "@babel/plugin-syntax-function-sent"; import syntaxFunctionSent from "@babel/plugin-syntax-function-sent";
import syntaxModuleBlocks from "@babel/plugin-syntax-module-blocks";
import syntaxImportMeta from "@babel/plugin-syntax-import-meta"; import syntaxImportMeta from "@babel/plugin-syntax-import-meta";
import syntaxJsx from "@babel/plugin-syntax-jsx"; import syntaxJsx from "@babel/plugin-syntax-jsx";
import syntaxImportAssertions from "@babel/plugin-syntax-import-assertions"; import syntaxImportAssertions from "@babel/plugin-syntax-import-assertions";
@ -107,6 +108,7 @@ export {
syntaxFlow, syntaxFlow,
syntaxFunctionBind, syntaxFunctionBind,
syntaxFunctionSent, syntaxFunctionSent,
syntaxModuleBlocks,
syntaxImportMeta, syntaxImportMeta,
syntaxJsx, syntaxJsx,
syntaxImportAssertions, syntaxImportAssertions,
@ -202,6 +204,7 @@ export const all = {
"syntax-flow": syntaxFlow, "syntax-flow": syntaxFlow,
"syntax-function-bind": syntaxFunctionBind, "syntax-function-bind": syntaxFunctionBind,
"syntax-function-sent": syntaxFunctionSent, "syntax-function-sent": syntaxFunctionSent,
"syntax-module-blocks": syntaxModuleBlocks,
"syntax-import-meta": syntaxImportMeta, "syntax-import-meta": syntaxImportMeta,
"syntax-jsx": syntaxJsx, "syntax-jsx": syntaxJsx,
"syntax-import-assertions": syntaxImportAssertions, "syntax-import-assertions": syntaxImportAssertions,

View File

@ -22,6 +22,7 @@ export default (_: any, opts: Object = {}) => {
plugins: [ plugins: [
babelPlugins.syntaxDecimal, babelPlugins.syntaxDecimal,
[babelPlugins.syntaxRecordAndTuple, { syntaxType: recordAndTupleSyntax }], [babelPlugins.syntaxRecordAndTuple, { syntaxType: recordAndTupleSyntax }],
babelPlugins.syntaxModuleBlocks,
babelPlugins.proposalExportDefaultFrom, babelPlugins.proposalExportDefaultFrom,
[babelPlugins.proposalPipelineOperator, { proposal: pipelineProposal }], [babelPlugins.proposalPipelineOperator, { proposal: pipelineProposal }],
babelPlugins.proposalDoExpressions, babelPlugins.proposalDoExpressions,

View File

@ -331,6 +331,9 @@ export interface NodePathAssetions {
assertModuleDeclaration( assertModuleDeclaration(
opts?: object, opts?: object,
): asserts this is NodePath<t.ModuleDeclaration>; ): asserts this is NodePath<t.ModuleDeclaration>;
assertModuleExpression(
opts?: object,
): asserts this is NodePath<t.ModuleExpression>;
assertModuleSpecifier( assertModuleSpecifier(
opts?: object, opts?: object,
): asserts this is NodePath<t.ModuleSpecifier>; ): asserts this is NodePath<t.ModuleSpecifier>;

View File

@ -191,6 +191,7 @@ export interface NodePathValidators {
isMethod(opts?: object): this is NodePath<t.Method>; isMethod(opts?: object): this is NodePath<t.Method>;
isMixedTypeAnnotation(opts?: object): this is NodePath<t.MixedTypeAnnotation>; isMixedTypeAnnotation(opts?: object): this is NodePath<t.MixedTypeAnnotation>;
isModuleDeclaration(opts?: object): this is NodePath<t.ModuleDeclaration>; isModuleDeclaration(opts?: object): this is NodePath<t.ModuleDeclaration>;
isModuleExpression(opts?: object): this is NodePath<t.ModuleExpression>;
isModuleSpecifier(opts?: object): this is NodePath<t.ModuleSpecifier>; isModuleSpecifier(opts?: object): this is NodePath<t.ModuleSpecifier>;
isNewExpression(opts?: object): this is NodePath<t.NewExpression>; isNewExpression(opts?: object): this is NodePath<t.NewExpression>;
isNoop(opts?: object): this is NodePath<t.Noop>; isNoop(opts?: object): this is NodePath<t.Noop>;

View File

@ -1088,6 +1088,12 @@ export function assertStaticBlock(
): asserts node is t.StaticBlock { ): asserts node is t.StaticBlock {
assert("StaticBlock", node, opts); assert("StaticBlock", node, opts);
} }
export function assertModuleExpression(
node: object | null | undefined,
opts?: object | null,
): asserts node is t.ModuleExpression {
assert("ModuleExpression", node, opts);
}
export function assertTSParameterProperty( export function assertTSParameterProperty(
node: object | null | undefined, node: object | null | undefined,
opts?: object | null, opts?: object | null,

View File

@ -182,6 +182,7 @@ export type Node =
| Method | Method
| MixedTypeAnnotation | MixedTypeAnnotation
| ModuleDeclaration | ModuleDeclaration
| ModuleExpression
| ModuleSpecifier | ModuleSpecifier
| NewExpression | NewExpression
| Noop | Noop
@ -1621,6 +1622,11 @@ export interface StaticBlock extends BaseNode {
body: Array<Statement>; body: Array<Statement>;
} }
export interface ModuleExpression extends BaseNode {
type: "ModuleExpression";
body: Program;
}
export interface TSParameterProperty extends BaseNode { export interface TSParameterProperty extends BaseNode {
type: "TSParameterProperty"; type: "TSParameterProperty";
parameter: Identifier | AssignmentPattern; parameter: Identifier | AssignmentPattern;
@ -2046,6 +2052,7 @@ export type Expression =
| RecordExpression | RecordExpression
| TupleExpression | TupleExpression
| DecimalLiteral | DecimalLiteral
| ModuleExpression
| TSAsExpression | TSAsExpression
| TSTypeAssertion | TSTypeAssertion
| TSNonNullExpression; | TSNonNullExpression;

View File

@ -1066,6 +1066,9 @@ export function decimalLiteral(value: string): t.DecimalLiteral {
export function staticBlock(body: Array<t.Statement>): t.StaticBlock { export function staticBlock(body: Array<t.Statement>): t.StaticBlock {
return builder("StaticBlock", ...arguments); return builder("StaticBlock", ...arguments);
} }
export function moduleExpression(body: t.Program): t.ModuleExpression {
return builder("ModuleExpression", ...arguments);
}
export function tsParameterProperty( export function tsParameterProperty(
parameter: t.Identifier | t.AssignmentPattern, parameter: t.Identifier | t.AssignmentPattern,
): t.TSParameterProperty { ): t.TSParameterProperty {

View File

@ -188,6 +188,7 @@ export {
tupleExpression as TupleExpression, tupleExpression as TupleExpression,
decimalLiteral as DecimalLiteral, decimalLiteral as DecimalLiteral,
staticBlock as StaticBlock, staticBlock as StaticBlock,
moduleExpression as ModuleExpression,
tsParameterProperty as TSParameterProperty, tsParameterProperty as TSParameterProperty,
tsDeclareFunction as TSDeclareFunction, tsDeclareFunction as TSDeclareFunction,
tsDeclareMethod as TSDeclareMethod, tsDeclareMethod as TSDeclareMethod,

View File

@ -262,3 +262,14 @@ defineType("StaticBlock", {
}, },
aliases: ["Scopable", "BlockParent"], aliases: ["Scopable", "BlockParent"],
}); });
// https://github.com/tc39/proposal-js-module-blocks
defineType("ModuleExpression", {
visitor: ["body"],
fields: {
body: {
validate: assertNodeType("Program"),
},
},
aliases: ["Expression"],
});

View File

@ -3048,6 +3048,23 @@ export function isStaticBlock(
return false; return false;
} }
export function isModuleExpression(
node: object | null | undefined,
opts?: object | null,
): node is t.ModuleExpression {
if (!node) return false;
const nodeType = (node as t.Node).type;
if (nodeType === "ModuleExpression") {
if (typeof opts === "undefined") {
return true;
} else {
return shallowEqual(node, opts);
}
}
return false;
}
export function isTSParameterProperty( export function isTSParameterProperty(
node: object | null | undefined, node: object | null | undefined,
opts?: object | null, opts?: object | null,
@ -4169,6 +4186,7 @@ export function isExpression(
"RecordExpression" === nodeType || "RecordExpression" === nodeType ||
"TupleExpression" === nodeType || "TupleExpression" === nodeType ||
"DecimalLiteral" === nodeType || "DecimalLiteral" === nodeType ||
"ModuleExpression" === nodeType ||
"TSAsExpression" === nodeType || "TSAsExpression" === nodeType ||
"TSTypeAssertion" === nodeType || "TSTypeAssertion" === nodeType ||
"TSNonNullExpression" === nodeType || "TSNonNullExpression" === nodeType ||

View File

@ -1656,6 +1656,16 @@ __metadata:
languageName: node languageName: node
linkType: hard linkType: hard
"@babel/plugin-syntax-module-blocks@workspace:*, @babel/plugin-syntax-module-blocks@workspace:packages/babel-plugin-syntax-module-blocks":
version: 0.0.0-use.local
resolution: "@babel/plugin-syntax-module-blocks@workspace:packages/babel-plugin-syntax-module-blocks"
dependencies:
"@babel/helper-plugin-utils": "workspace:^7.10.1"
peerDependencies:
"@babel/core": ^7.0.0-0
languageName: unknown
linkType: soft
"@babel/plugin-syntax-module-string-names@workspace:packages/babel-plugin-syntax-module-string-names": "@babel/plugin-syntax-module-string-names@workspace:packages/babel-plugin-syntax-module-string-names":
version: 0.0.0-use.local version: 0.0.0-use.local
resolution: "@babel/plugin-syntax-module-string-names@workspace:packages/babel-plugin-syntax-module-string-names" resolution: "@babel/plugin-syntax-module-string-names@workspace:packages/babel-plugin-syntax-module-string-names"
@ -3258,6 +3268,7 @@ __metadata:
"@babel/plugin-syntax-import-assertions": "workspace:*" "@babel/plugin-syntax-import-assertions": "workspace:*"
"@babel/plugin-syntax-import-meta": ^7.10.4 "@babel/plugin-syntax-import-meta": ^7.10.4
"@babel/plugin-syntax-jsx": "workspace:*" "@babel/plugin-syntax-jsx": "workspace:*"
"@babel/plugin-syntax-module-blocks": "workspace:*"
"@babel/plugin-syntax-object-rest-spread": ^7.8.0 "@babel/plugin-syntax-object-rest-spread": ^7.8.0
"@babel/plugin-syntax-optional-catch-binding": ^7.8.0 "@babel/plugin-syntax-optional-catch-binding": ^7.8.0
"@babel/plugin-syntax-pipeline-operator": "workspace:*" "@babel/plugin-syntax-pipeline-operator": "workspace:*"