@ibyar/expressions 0.5.1 → 0.5.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (187) hide show
  1. package/LICENSE +1 -1
  2. package/README.md +5 -4
  3. package/api/abstract.d.ts +5 -6
  4. package/api/abstract.js +3 -3
  5. package/api/abstract.js.map +1 -1
  6. package/api/class/class.d.ts +202 -0
  7. package/api/class/class.js +635 -0
  8. package/api/class/class.js.map +1 -0
  9. package/api/class/decorator.d.ts +20 -0
  10. package/api/class/decorator.js +48 -0
  11. package/api/class/decorator.js.map +1 -0
  12. package/api/computing/call.d.ts +3 -1
  13. package/api/computing/call.js +16 -4
  14. package/api/computing/call.js.map +1 -1
  15. package/api/computing/debugger.d.ts +15 -0
  16. package/api/computing/debugger.js +35 -0
  17. package/api/computing/debugger.js.map +1 -0
  18. package/api/computing/new.d.ts +2 -1
  19. package/api/computing/new.js +4 -0
  20. package/api/computing/new.js.map +1 -1
  21. package/api/computing/rest.d.ts +6 -6
  22. package/api/computing/rest.js +5 -2
  23. package/api/computing/rest.js.map +1 -1
  24. package/api/computing/return.d.ts +2 -1
  25. package/api/computing/return.js +3 -0
  26. package/api/computing/return.js.map +1 -1
  27. package/api/computing/spread.d.ts +2 -1
  28. package/api/computing/spread.js +5 -2
  29. package/api/computing/spread.js.map +1 -1
  30. package/api/computing/throw.d.ts +2 -1
  31. package/api/computing/throw.js +3 -0
  32. package/api/computing/throw.js.map +1 -1
  33. package/api/computing/yield.d.ts +2 -1
  34. package/api/computing/yield.js +3 -0
  35. package/api/computing/yield.js.map +1 -1
  36. package/api/definition/array.d.ts +12 -12
  37. package/api/definition/array.js +31 -25
  38. package/api/definition/array.js.map +1 -1
  39. package/api/definition/bind.d.ts +2 -2
  40. package/api/definition/bind.js +1 -1
  41. package/api/definition/bind.js.map +1 -1
  42. package/api/definition/function.d.ts +40 -51
  43. package/api/definition/function.js +291 -309
  44. package/api/definition/function.js.map +1 -1
  45. package/api/definition/member.d.ts +2 -2
  46. package/api/definition/member.js +1 -1
  47. package/api/definition/member.js.map +1 -1
  48. package/api/definition/object.d.ts +15 -12
  49. package/api/definition/object.js +43 -13
  50. package/api/definition/object.js.map +1 -1
  51. package/api/definition/statement.d.ts +2 -2
  52. package/api/definition/statement.js +7 -3
  53. package/api/definition/statement.js.map +1 -1
  54. package/api/definition/values.d.ts +35 -50
  55. package/api/definition/values.js +66 -149
  56. package/api/definition/values.js.map +1 -1
  57. package/api/deserialize/deserialize.d.ts +2 -1
  58. package/api/deserialize/deserialize.js +4 -1
  59. package/api/deserialize/deserialize.js.map +1 -1
  60. package/api/deserialize/type-store.d.ts +2 -2
  61. package/api/deserialize/type-store.js.map +1 -1
  62. package/api/expression.d.ts +13 -18
  63. package/api/expression.js.map +1 -1
  64. package/api/index.d.ts +2 -0
  65. package/api/index.js +2 -0
  66. package/api/index.js.map +1 -1
  67. package/api/module/common.d.ts +29 -0
  68. package/api/module/common.js +71 -0
  69. package/api/module/common.js.map +1 -0
  70. package/api/module/export.d.ts +66 -25
  71. package/api/module/export.js +270 -58
  72. package/api/module/export.js.map +1 -1
  73. package/api/module/import.d.ts +61 -25
  74. package/api/module/import.js +226 -68
  75. package/api/module/import.js.map +1 -1
  76. package/api/operators/assignment.d.ts +2 -2
  77. package/api/operators/assignment.js +1 -1
  78. package/api/operators/assignment.js.map +1 -1
  79. package/api/operators/await.d.ts +2 -2
  80. package/api/operators/await.js +1 -1
  81. package/api/operators/await.js.map +1 -1
  82. package/api/operators/binary.d.ts +2 -2
  83. package/api/operators/binary.js +1 -1
  84. package/api/operators/binary.js.map +1 -1
  85. package/api/operators/chaining.d.ts +2 -2
  86. package/api/operators/chaining.js +1 -1
  87. package/api/operators/chaining.js.map +1 -1
  88. package/api/operators/comma.d.ts +2 -2
  89. package/api/operators/comma.js +2 -2
  90. package/api/operators/comma.js.map +1 -1
  91. package/api/operators/grouping.d.ts +2 -2
  92. package/api/operators/grouping.js +1 -1
  93. package/api/operators/grouping.js.map +1 -1
  94. package/api/operators/logical.d.ts +2 -2
  95. package/api/operators/logical.js +1 -1
  96. package/api/operators/logical.js.map +1 -1
  97. package/api/operators/pipeline.d.ts +2 -2
  98. package/api/operators/pipeline.js +1 -1
  99. package/api/operators/pipeline.js.map +1 -1
  100. package/api/operators/ternary.d.ts +2 -2
  101. package/api/operators/ternary.js +1 -1
  102. package/api/operators/ternary.js.map +1 -1
  103. package/api/operators/unary.d.ts +3 -3
  104. package/api/operators/unary.js +4 -3
  105. package/api/operators/unary.js.map +1 -1
  106. package/api/operators/update.d.ts +2 -2
  107. package/api/operators/update.js +1 -1
  108. package/api/operators/update.js.map +1 -1
  109. package/api/{app/program.d.ts → program.d.ts} +8 -9
  110. package/api/program.js +45 -0
  111. package/api/program.js.map +1 -0
  112. package/api/statement/control/block.d.ts +4 -5
  113. package/api/statement/control/block.js +22 -23
  114. package/api/statement/control/block.js.map +1 -1
  115. package/api/statement/control/empty.d.ts +1 -1
  116. package/api/statement/control/empty.js.map +1 -1
  117. package/api/statement/control/if.d.ts +2 -2
  118. package/api/statement/control/if.js +1 -1
  119. package/api/statement/control/if.js.map +1 -1
  120. package/api/statement/control/switch.d.ts +4 -5
  121. package/api/statement/control/switch.js +13 -9
  122. package/api/statement/control/switch.js.map +1 -1
  123. package/api/statement/control/terminate.d.ts +38 -13
  124. package/api/statement/control/terminate.js +81 -20
  125. package/api/statement/control/terminate.js.map +1 -1
  126. package/api/statement/declarations/declares.d.ts +17 -16
  127. package/api/statement/declarations/declares.js +24 -19
  128. package/api/statement/declarations/declares.js.map +1 -1
  129. package/api/statement/iterations/for.d.ts +5 -5
  130. package/api/statement/iterations/for.js +29 -23
  131. package/api/statement/iterations/for.js.map +1 -1
  132. package/api/statement/iterations/while.d.ts +3 -3
  133. package/api/statement/iterations/while.js +17 -13
  134. package/api/statement/iterations/while.js.map +1 -1
  135. package/api/utils.d.ts +5 -0
  136. package/api/utils.js +4 -0
  137. package/api/utils.js.map +1 -0
  138. package/package.json +5 -5
  139. package/scope/event.d.ts +2 -2
  140. package/scope/event.js +8 -14
  141. package/scope/event.js.map +1 -1
  142. package/scope/finalizer.d.ts +4 -0
  143. package/scope/finalizer.js +11 -0
  144. package/scope/finalizer.js.map +1 -0
  145. package/scope/proxy.d.ts +2 -3
  146. package/scope/proxy.js +22 -26
  147. package/scope/proxy.js.map +1 -1
  148. package/scope/scope.d.ts +42 -53
  149. package/scope/scope.js +73 -143
  150. package/scope/scope.js.map +1 -1
  151. package/scope/stack.d.ts +43 -26
  152. package/scope/stack.js +148 -102
  153. package/scope/stack.js.map +1 -1
  154. package/v8/enums.d.ts +204 -0
  155. package/v8/enums.js +375 -0
  156. package/v8/enums.js.map +1 -0
  157. package/v8/index.d.ts +2 -1
  158. package/v8/index.js +2 -1
  159. package/v8/index.js.map +1 -1
  160. package/v8/inline.d.ts +177 -0
  161. package/v8/inline.js +1973 -0
  162. package/v8/inline.js.map +1 -0
  163. package/v8/nodes.d.ts +8 -7
  164. package/v8/nodes.js +37 -63
  165. package/v8/nodes.js.map +1 -1
  166. package/v8/parser.d.ts +41 -151
  167. package/v8/parser.js +507 -1578
  168. package/v8/parser.js.map +1 -1
  169. package/v8/stream.d.ts +35 -3
  170. package/v8/stream.js +616 -164
  171. package/v8/stream.js.map +1 -1
  172. package/v8/token.d.ts +15 -9
  173. package/v8/token.js +79 -46
  174. package/v8/token.js.map +1 -1
  175. package/visit/visitor.js +4 -7
  176. package/visit/visitor.js.map +1 -1
  177. package/api/app/class.d.ts +0 -117
  178. package/api/app/class.js +0 -292
  179. package/api/app/class.js.map +0 -1
  180. package/api/app/program.js +0 -39
  181. package/api/app/program.js.map +0 -1
  182. package/api/module/module.d.ts +0 -26
  183. package/api/module/module.js +0 -63
  184. package/api/module/module.js.map +0 -1
  185. package/v8/app.d.ts +0 -0
  186. package/v8/app.js +0 -2
  187. package/v8/app.js.map +0 -1
package/v8/parser.js CHANGED
@@ -1,1716 +1,645 @@
1
+ import { JavaScriptInlineParser } from './inline.js';
1
2
  import { Token } from './token.js';
2
- import { TokenStream } from './stream.js';
3
- import { OfNode, Identifier, ThisNode, GetIdentifier, SetIdentifier, AsyncIdentifier, NullNode, StringLiteral, AwaitIdentifier, ConstructorIdentifier, NameIdentifier, EvalIdentifier, ArgumentsIdentifier, TaggedTemplateExpression, TemplateLiteral } from '../api/definition/values.js';
4
- import { EmptyStatement } from '../api/statement/control/empty.js';
5
- import { BlockStatement } from '../api/statement/control/block.js';
6
- import { ArrowFunctionExpression, ArrowFunctionType, FunctionKind, Param, FunctionExpression, FunctionDeclaration } from '../api/definition/function.js';
7
- import { IfStatement } from '../api/statement/control/if.js';
8
- import { NewExpression } from '../api/computing/new.js';
9
- import { SpreadElement } from '../api/computing/spread.js';
10
- import { RestElement } from '../api/computing/rest.js';
3
+ import { Class, ClassBody, ClassDeclaration, ClassExpression, MetaProperty, MethodDefinition, PropertyDefinition, StaticBlock, Super } from '../api/class/class.js';
4
+ import { Identifier, Literal, NullNode } from '../api/definition/values.js';
11
5
  import { AssignmentExpression } from '../api/operators/assignment.js';
12
- import { GroupingExpression } from '../api/operators/grouping.js';
13
- import { MemberExpression } from '../api/definition/member.js';
14
- import { BindExpression } from '../api/definition/bind.js';
15
- import { ObjectExpression, Property, ObjectPattern } from '../api/definition/object.js';
16
- import { ArrayExpression, ArrayPattern } from '../api/definition/array.js';
17
- import { CallExpression } from '../api/computing/call.js';
18
- import { DoWhileNode, WhileNode } from '../api/statement/iterations/while.js';
19
- import { CatchClauseNode, ThrowStatement, TryCatchNode } from '../api/computing/throw.js';
20
- import { SwitchCase, DefaultExpression, SwitchStatement } from '../api/statement/control/switch.js';
21
- import { BreakStatement, ContinueStatement } from '../api/statement/control/terminate.js';
22
- import { ReturnStatement } from '../api/computing/return.js';
23
- import { YieldExpression } from '../api/computing/yield.js';
24
- import { VariableNode, VariableDeclarationNode } from '../api/statement/declarations/declares.js';
25
- import { ForNode, ForOfNode, ForInNode, ForAwaitOfNode } from '../api/statement/iterations/for.js';
26
- import { ConditionalExpression } from '../api/operators/ternary.js';
27
- import { PipelineExpression } from '../api/operators/pipeline.js';
28
- import { LogicalExpression } from '../api/operators/logical.js';
29
- import { SequenceExpression } from '../api/operators/comma.js';
30
- import { ChainExpression } from '../api/operators/chaining.js';
31
- import { ExpressionStatement } from '../api/definition/statement.js';
32
- import { buildPostfixExpression, buildUnaryExpression, expressionFromLiteral, shortcutNumericLiteralBinaryExpression } from './nodes.js';
33
- import { BinaryExpression } from '../api/operators/binary.js';
34
- export var ParsingArrowHeadFlag;
35
- (function (ParsingArrowHeadFlag) {
36
- ParsingArrowHeadFlag[ParsingArrowHeadFlag["CertainlyNotArrowHead"] = 0] = "CertainlyNotArrowHead";
37
- ParsingArrowHeadFlag[ParsingArrowHeadFlag["MaybeArrowHead"] = 1] = "MaybeArrowHead";
38
- ParsingArrowHeadFlag[ParsingArrowHeadFlag["AsyncArrowFunction"] = 2] = "AsyncArrowFunction";
39
- })(ParsingArrowHeadFlag || (ParsingArrowHeadFlag = {}));
40
- export var PropertyKind;
41
- (function (PropertyKind) {
42
- PropertyKind[PropertyKind["Value"] = 0] = "Value";
43
- PropertyKind[PropertyKind["Shorthand"] = 1] = "Shorthand";
44
- PropertyKind[PropertyKind["ShorthandOrClassField"] = 2] = "ShorthandOrClassField";
45
- PropertyKind[PropertyKind["Assign"] = 3] = "Assign";
46
- PropertyKind[PropertyKind["Method"] = 4] = "Method";
47
- PropertyKind[PropertyKind["ClassField"] = 5] = "ClassField";
48
- PropertyKind[PropertyKind["AccessorGetter"] = 6] = "AccessorGetter";
49
- PropertyKind[PropertyKind["AccessorSetter"] = 7] = "AccessorSetter";
50
- PropertyKind[PropertyKind["Spread"] = 8] = "Spread";
51
- PropertyKind[PropertyKind["NotSet"] = 9] = "NotSet";
52
- })(PropertyKind || (PropertyKind = {}));
53
- export function parsePropertyKindFromToken(token, info) {
54
- switch (token) {
55
- case Token.COLON:
56
- info.kind = PropertyKind.Value;
57
- return true;
58
- case Token.COMMA:
59
- info.kind = PropertyKind.Shorthand;
60
- return true;
61
- case Token.R_CURLY:
62
- info.kind = PropertyKind.ShorthandOrClassField;
63
- return true;
64
- case Token.ASSIGN:
65
- info.kind = PropertyKind.Assign;
66
- return true;
67
- case Token.L_PARENTHESES:
68
- info.kind = PropertyKind.Method;
69
- return true;
70
- case Token.MUL:
71
- case Token.SEMICOLON:
72
- info.kind = PropertyKind.ClassField;
73
- return true;
74
- default:
75
- break;
76
- }
77
- return false;
78
- }
79
- export var PreParserIdentifierType;
80
- (function (PreParserIdentifierType) {
81
- PreParserIdentifierType["NullIdentifier"] = "NullIdentifier";
82
- PreParserIdentifierType["UnknownIdentifier"] = "UnknownIdentifier";
83
- PreParserIdentifierType["EvalIdentifier"] = "EvalIdentifier";
84
- PreParserIdentifierType["ArgumentsIdentifier"] = "ArgumentsIdentifier";
85
- PreParserIdentifierType["ConstructorIdentifier"] = "ConstructorIdentifier";
86
- PreParserIdentifierType["AwaitIdentifier"] = "AwaitIdentifier";
87
- PreParserIdentifierType["AsyncIdentifier"] = "AsyncIdentifier";
88
- PreParserIdentifierType["NameIdentifier"] = "NameIdentifier";
89
- PreParserIdentifierType["PrivateNameIdentifier"] = "PrivateNameIdentifier";
90
- })(PreParserIdentifierType || (PreParserIdentifierType = {}));
91
- export class AbstractParser {
92
- constructor(scanner) {
93
- this.scanner = scanner;
94
- }
95
- position() {
96
- return this.scanner.getPos();
97
- }
98
- current() {
99
- return this.scanner.currentToken();
100
- }
101
- next() {
102
- return this.scanner.next();
103
- }
104
- peek() {
105
- return this.scanner.peek();
106
- }
107
- peekAhead() {
108
- return this.scanner.peekAhead();
109
- }
110
- peekAheadPosition() {
111
- return this.scanner.peekAheadPosition();
112
- }
113
- peekPosition() {
114
- return this.scanner.peekPosition();
115
- }
116
- consume(token) {
117
- if (this.scanner.next().isNotType(token)) {
118
- throw new Error(this.errorMessage(`Parsing ${JSON.stringify(token)}`));
119
- }
120
- }
121
- check(token) {
122
- const next = this.scanner.peek();
123
- if (next.isType(token)) {
124
- this.scanner.next();
125
- return true;
126
- }
127
- return false;
128
- }
129
- checkValue(value) {
130
- const next = this.scanner.peek();
131
- if (next.value == value) {
132
- this.scanner.next();
133
- return true;
134
- }
135
- return false;
136
- }
137
- expect(token) {
138
- const current = this.scanner.next();
139
- if (current.isNotType(token)) {
140
- throw new Error(this.errorMessage(`Unexpected Token: ${JSON.stringify(token)}, current is ${JSON.stringify(current)}`));
141
- }
142
- }
143
- checkInOrOf() {
144
- if (this.check(Token.IN)) {
145
- return 'IN';
146
- }
147
- else if (this.checkValue(OfNode)) {
148
- return 'OF';
149
- }
150
- return false;
151
- }
152
- peekInOrOf() {
153
- var next = this.peek();
154
- if (next.isType(Token.IN)) {
155
- return 'IN';
156
- }
157
- else if (next.value === OfNode) {
158
- return 'OF';
159
- }
160
- return false;
161
- }
162
- isEvalOrArguments(name) {
163
- if (name.toString() === 'eval') {
164
- return true;
165
- }
166
- else if (name.toString() === 'arguments') {
167
- return true;
168
- }
169
- return false;
170
- }
171
- isNextLetKeyword() {
172
- if (this.peek().isNotType(Token.LET)) {
173
- return false;
174
- }
175
- const nextNextToken = this.peekAhead().token;
176
- switch (nextNextToken) {
177
- case Token.L_CURLY:
178
- case Token.L_BRACKETS:
179
- case Token.IDENTIFIER:
180
- case Token.STATIC:
181
- case Token.LET:
182
- case Token.YIELD:
183
- case Token.AWAIT:
184
- case Token.GET:
185
- case Token.SET:
186
- case Token.ASYNC:
187
- return true;
188
- default:
189
- return false;
190
- }
191
- }
192
- isIdentifier(expression) {
193
- return expression instanceof Identifier;
6
+ import { VariableDeclarationNode, VariableDeclarator } from '../api/statement/declarations/declares.js';
7
+ import { TokenStream } from './stream.js';
8
+ import { Program } from '../api/program.js';
9
+ import { ExportAllDeclaration, ExportDefaultDeclaration, ExportNamedDeclaration, ExportSpecifier } from '../api/module/export.js';
10
+ import { ImportDeclaration, ImportDefaultSpecifier, ImportExpression, ImportNamespaceSpecifier, ImportSpecifier } from '../api/module/import.js';
11
+ import { ImportAttribute } from '../api/module/common.js';
12
+ import { ClassLiteralProperty, ClassLiteralPropertyKind, classPropertyKindFor, createClassInfo, FunctionKind, FunctionSyntaxKind, isAccessor, isStrict, LanguageMode, ParseFunctionFlag, PropertyKind, PropertyKindInfo, PropertyPosition, VariableDeclarationContext } from './enums.js';
13
+ export class JavaScriptParser extends JavaScriptInlineParser {
14
+ static parse(source, { mode } = {}) {
15
+ mode ?? (mode = LanguageMode.Strict);
16
+ const stream = (typeof source === 'string') || Array.isArray(source)
17
+ ? TokenStream.getTokenStream(source, mode) : source;
18
+ const parser = new JavaScriptParser(stream);
19
+ return parser.scan();
194
20
  }
195
- isParenthesized(expression) {
196
- return expression instanceof GroupingExpression || expression instanceof SequenceExpression;
21
+ static parseScript(source, options) {
22
+ return JavaScriptInlineParser.parse(source, options);
197
23
  }
198
- isAssignableIdentifier(expression) {
199
- if (!(expression instanceof Identifier)) {
200
- return false;
201
- }
202
- if (this.isEvalOrArguments(expression)) {
203
- return false;
24
+ scan() {
25
+ const isModule = isStrict(this.languageMode);
26
+ if (isModule) {
27
+ this.setFunctionKind(FunctionKind.Module);
204
28
  }
205
- return true;
206
- }
207
- isPattern(expression) {
208
- return expression instanceof ObjectPattern || expression instanceof ArrayPattern;
209
- }
210
- isProperty(expression) {
211
- return expression instanceof MemberExpression;
212
- }
213
- isCallNew(expression) {
214
- return expression instanceof NewExpression;
29
+ const body = isModule ? this.parseModuleItemList() : this.parseStatementList(Token.EOS);
30
+ return new Program(isModule ? 'module' : 'script', body);
215
31
  }
216
- isCall(expression) {
217
- return expression instanceof CallExpression;
218
- }
219
- isEmptyStatement(expression) {
220
- return expression instanceof EmptyStatement;
221
- }
222
- isThisProperty(expression) {
223
- if (this.isProperty(expression)) {
224
- if (expression.getObject() === ThisNode || expression.getObject().toString() === 'this') {
225
- return true;
226
- }
32
+ parseNewTargetExpression() {
33
+ this.consume(Token.PERIOD);
34
+ const target = this.parsePropertyOrPrivatePropertyName();
35
+ if (target.toString() !== 'target') {
36
+ throw new Error(this.errorMessage(`Expression (new.${target.toString()}) not supported.`));
227
37
  }
228
- return false;
38
+ return MetaProperty.NewTarget;
229
39
  }
230
- isValidReferenceExpression(expression) {
231
- return this.isAssignableIdentifier(expression) || this.isProperty(expression);
232
- }
233
- expectSemicolon() {
234
- const tok = this.peek();
235
- if (tok.isType(Token.SEMICOLON)) {
236
- this.next();
237
- return;
238
- }
239
- if (this.scanner.hasLineTerminatorBeforeNext() || Token.isAutoSemicolon(tok.token)) {
240
- return;
241
- }
242
- if (this.scanner.currentToken().isType(Token.AWAIT)) {
243
- throw new Error(this.errorMessage(`Await Not In Async Context/Function`));
40
+ parseClassExpression() {
41
+ this.consume(Token.CLASS);
42
+ let name;
43
+ let isStrictReserved = false;
44
+ if (this.peekAnyIdentifier()) {
45
+ name = this.parseAndClassifyIdentifier(this.next());
46
+ isStrictReserved = Token.isStrictReservedWord(this.current().token);
244
47
  }
48
+ const classLiteral = this.parseClassLiteral(name, isStrictReserved);
49
+ return new ClassExpression(classLiteral.getBody(), classLiteral.getDecorators(), classLiteral.getId(), classLiteral.getSuperClass());
245
50
  }
246
- peekAnyIdentifier() {
247
- return Token.isAnyIdentifier(this.peek().token);
248
- }
249
- errorMessage(message) {
250
- return this.scanner.createError(message);
251
- }
252
- }
253
- export class JavaScriptParser extends AbstractParser {
254
- static parse(source) {
255
- const stream = (typeof source === 'string' || Array.isArray(source))
256
- ? TokenStream.getTokenStream(source)
257
- : source;
258
- const parser = new JavaScriptParser(stream);
259
- return parser.scan();
260
- }
261
- scan() {
262
- const list = this.parseStatementList(Token.EOS);
263
- if (list.length === 1) {
264
- return list[0];
51
+ parseClassDeclaration(names, defaultExport) {
52
+ const nextToken = this.peek().token;
53
+ const isStrictReserved = Token.isStrictReservedWord(nextToken);
54
+ let name;
55
+ let variableName;
56
+ if (defaultExport && (nextToken == Token.EXTENDS || nextToken == Token.LBRACE)) {
57
+ name = new Literal('default');
58
+ variableName = '.default';
265
59
  }
266
- return new ExpressionStatement(list);
267
- }
268
- parseStatement() {
269
- switch (this.peek().token) {
270
- case Token.L_CURLY:
271
- return this.parseBlock();
272
- case Token.SEMICOLON:
273
- this.consume(Token.SEMICOLON);
274
- return EmptyStatement.INSTANCE;
275
- case Token.IF:
276
- return this.parseIfStatement();
277
- case Token.DO:
278
- return this.parseDoWhileStatement();
279
- case Token.WHILE:
280
- return this.parseWhileStatement();
281
- case Token.FOR:
282
- return this.parseForStatement();
283
- case Token.CONTINUE:
284
- return this.parseContinueStatement();
285
- case Token.BREAK:
286
- return this.parseBreakStatement();
287
- case Token.RETURN:
288
- return this.parseReturnStatement();
289
- case Token.THROW:
290
- return this.parseThrowStatement();
291
- case Token.TRY:
292
- return this.parseTryStatement();
293
- case Token.SWITCH:
294
- return this.parseSwitchStatement();
295
- case Token.VAR:
296
- case Token.LET:
297
- case Token.CONST:
298
- return this.parseVariableDeclarations();
299
- case Token.ASYNC:
300
- if (this.peekAhead().isType(Token.FUNCTION)) {
301
- this.consume(Token.ASYNC);
302
- this.consume(Token.FUNCTION);
303
- if (this.peek().isType(Token.MUL)) {
304
- return this.parseFunctionExpression(FunctionKind.ASYNC_GENERATOR);
305
- }
306
- return this.parseFunctionExpression(FunctionKind.ASYNC);
307
- }
308
- default:
309
- return this.parseExpressionOrLabelledStatement();
60
+ else {
61
+ const identifier = this.parseIdentifier();
62
+ variableName = identifier.getName();
63
+ name = identifier;
310
64
  }
65
+ const classLiteral = this.parseClassLiteral(name, isStrictReserved);
66
+ return new ClassDeclaration(classLiteral.getBody(), classLiteral.getDecorators(), classLiteral.getId(), classLiteral.getSuperClass());
311
67
  }
312
- parseTryStatement() {
313
- this.consume(Token.TRY);
314
- const tryBlock = this.parseBlock();
315
- if (tryBlock instanceof BlockStatement) {
316
- tryBlock.isStatement = true;
317
- }
318
- let peek = this.peek();
319
- if (peek.isNotType(Token.CATCH) && peek.isNotType(Token.FINALLY)) {
320
- throw new Error(this.errorMessage(`Uncaught SyntaxError: Missing catch or finally after try`));
321
- }
322
- let catchBlock;
323
- if (this.check(Token.CATCH)) {
324
- let catchVar;
325
- const hasBinding = this.check(Token.L_PARENTHESES);
326
- if (hasBinding) {
327
- catchVar = this.parseIdentifier();
328
- this.expect(Token.R_PARENTHESES);
68
+ parseClassLiteral(name, nameIsStrictReserved) {
69
+ const isAnonymous = !!!name;
70
+ if (!isAnonymous) {
71
+ if (nameIsStrictReserved) {
72
+ throw new Error(this.errorMessage(`Unexpected Strict Reserved class name`));
329
73
  }
330
- const block = this.parseBlock();
331
- if (block instanceof BlockStatement) {
332
- block.isStatement = true;
74
+ if (this.isEvalOrArguments(name)) {
75
+ throw new Error(this.errorMessage(`Strict Eval Arguments not allowed for class name`));
333
76
  }
334
- catchBlock = new CatchClauseNode(block, catchVar);
335
77
  }
336
- let finallyBlock;
337
- if (this.check(Token.FINALLY)) {
338
- finallyBlock = this.parseBlock();
339
- if (finallyBlock instanceof BlockStatement) {
340
- finallyBlock.isStatement = true;
341
- }
78
+ const classInfo = createClassInfo();
79
+ classInfo.isAnonymous = isAnonymous;
80
+ if (this.check(Token.EXTENDS)) {
81
+ classInfo.extends = this.parseLeftHandSideExpression();
342
82
  }
343
- return new TryCatchNode(tryBlock, catchBlock, finallyBlock);
344
- }
345
- parseBlock() {
346
- this.expect(Token.L_CURLY);
347
- const statements = [];
348
- const block = new BlockStatement(statements, false);
349
- while (this.peek().isNotType(Token.R_CURLY)) {
350
- const stat = this.parseStatementListItem();
351
- if (!stat) {
352
- return block;
83
+ this.expect(Token.LBRACE);
84
+ const hasExtends = !!classInfo.extends;
85
+ while (this.peek().isNotType(Token.RBRACE)) {
86
+ if (this.check(Token.SEMICOLON))
87
+ continue;
88
+ if (this.peek().isType(Token.STATIC) && this.peekAhead().isType(Token.LBRACE)) {
89
+ const staticBlock = this.parseClassStaticBlock(classInfo);
90
+ classInfo.staticElements.push(staticBlock);
91
+ classInfo.hasStaticBlocks = true;
92
+ continue;
353
93
  }
354
- else if (stat instanceof EmptyStatement) {
94
+ let isConstructor = !classInfo.hasSeenConstructor;
95
+ const propInfo = new PropertyKindInfo();
96
+ propInfo.position = PropertyPosition.ClassLiteral;
97
+ const property = this.parseClassPropertyDefinition(classInfo, propInfo, hasExtends);
98
+ const propertyKind = classPropertyKindFor(propInfo.kind);
99
+ if (!classInfo.hasStaticComputedNames && propInfo.isStatic && propInfo.isComputedName) {
100
+ classInfo.hasStaticComputedNames = true;
101
+ }
102
+ isConstructor && (isConstructor = classInfo.hasSeenConstructor);
103
+ const isField = propertyKind == ClassLiteralPropertyKind.FIELD;
104
+ if (propInfo.isPrivate) {
105
+ if (isConstructor) {
106
+ throw new Error(this.errorMessage('private constructor is not allowed'));
107
+ }
108
+ classInfo.requiresBrand || (classInfo.requiresBrand = !isField && !propInfo.isStatic);
109
+ const isMethod = propertyKind == ClassLiteralPropertyKind.METHOD;
110
+ classInfo.hasPrivateMethods || (classInfo.hasPrivateMethods = isMethod);
111
+ classInfo.hasStaticPrivateMethods || (classInfo.hasStaticPrivateMethods = isMethod && propInfo.isStatic);
112
+ this.declarePrivateClassMember(propInfo.name, property, propertyKind, propInfo.isStatic, classInfo);
355
113
  continue;
356
114
  }
357
- statements.push(stat);
358
- }
359
- this.expect(Token.R_CURLY);
360
- return block;
361
- }
362
- parseStatementListItem() {
363
- switch (this.peek().token) {
364
- case Token.FUNCTION:
365
- this.consume(Token.FUNCTION);
366
- if (this.peek().isType(Token.MUL)) {
367
- this.consume(Token.MUL);
368
- return this.parseFunctionExpression(FunctionKind.GENERATOR);
369
- }
370
- return this.parseFunctionExpression(FunctionKind.NORMAL);
371
- case Token.CLASS:
372
- this.consume(Token.CLASS);
373
- return this.parseClassDeclaration(undefined, false);
374
- case Token.VAR:
375
- case Token.LET:
376
- case Token.CONST:
377
- return this.parseVariableDeclarations();
378
- case Token.ASYNC:
379
- if (this.peekAhead().isType(Token.FUNCTION)) {
380
- this.consume(Token.ASYNC);
381
- this.consume(Token.FUNCTION);
382
- if (this.peek().isType(Token.MUL)) {
383
- this.consume(Token.MUL);
384
- return this.parseFunctionExpression(FunctionKind.ASYNC_GENERATOR);
385
- }
386
- return this.parseFunctionExpression(FunctionKind.ASYNC);
115
+ if (isField) {
116
+ if (propInfo.isComputedName) {
117
+ classInfo.computedFieldCount++;
387
118
  }
388
- break;
389
- default:
390
- break;
119
+ this.declarePublicClassField(property, propInfo.isStatic, propInfo.isComputedName, classInfo);
120
+ continue;
121
+ }
122
+ this.declarePublicClassMethod(name, property, isConstructor, classInfo);
391
123
  }
392
- return this.parseStatement();
124
+ this.expect(Token.RBRACE);
125
+ const classBody = this.rewriteClassLiteral(classInfo, name);
126
+ return new Class(classBody, [], name, classInfo.extends);
393
127
  }
394
- parseFunctionExpression(type) {
395
- let funcName;
396
- const peek = this.peek();
397
- if (peek.isNotType(Token.L_PARENTHESES)) {
398
- if (peek.isType(Token.L_BRACKETS)) {
399
- this.consume(Token.L_BRACKETS);
400
- funcName = this.parseMemberExpression();
401
- this.expect(Token.R_BRACKETS);
402
- }
403
- else {
404
- funcName = this.parseIdentifier();
128
+ declarePublicClassMethod(name, property, isConstructor, classInfo) {
129
+ if (isConstructor) {
130
+ if (classInfo.constructor) {
131
+ throw new SyntaxError(this.errorMessage('A class may only have one constructor.'));
405
132
  }
133
+ classInfo.constructor = property;
134
+ Reflect.set(classInfo.constructor, 'id', name);
135
+ return;
406
136
  }
407
- return this.parseFunctionLiteral(type, funcName);
137
+ classInfo.publicMembers.push(property);
408
138
  }
409
- parseIfStatement() {
410
- this.consume(Token.IF);
411
- this.consume(Token.L_PARENTHESES);
412
- const condition = this.parseExpression();
413
- this.consume(Token.R_PARENTHESES);
414
- const thenStatement = this.parseStatement();
415
- if (thenStatement instanceof BlockStatement) {
416
- thenStatement.isStatement = true;
139
+ declarePublicClassField(property, isStatic, isComputedName, classInfo) {
140
+ if (isStatic) {
141
+ classInfo.staticElements.push(property);
417
142
  }
418
- let elseStatement;
419
- if (this.peek().isType(Token.ELSE)) {
420
- this.consume(Token.ELSE);
421
- elseStatement = this.parseStatement();
143
+ else {
144
+ classInfo.instanceFields.push(property);
422
145
  }
423
- return new IfStatement(condition, thenStatement, elseStatement);
424
146
  }
425
- parseDoWhileStatement() {
426
- this.consume(Token.DO);
427
- const body = this.parseStatement();
428
- if (body instanceof BlockStatement) {
429
- body.isStatement = true;
430
- }
431
- this.expect(Token.WHILE);
432
- this.expect(Token.L_PARENTHESES);
433
- const condition = this.parseExpression();
434
- this.expect(Token.R_PARENTHESES);
435
- this.check(Token.SEMICOLON);
436
- return new DoWhileNode(condition, body);
147
+ declarePrivateClassMember(propertyName, property, kind, isStatic, classInfo) {
148
+ classInfo.privateMembers.push(property);
437
149
  }
438
- parseWhileStatement() {
439
- this.consume(Token.WHILE);
440
- this.expect(Token.L_PARENTHESES);
441
- const condition = this.parseExpression();
442
- this.expect(Token.R_PARENTHESES);
443
- const body = this.parseStatement();
444
- if (body instanceof BlockStatement) {
445
- body.isStatement = true;
150
+ parseClassPropertyDefinition(classInfo, propInfo, hasExtends) {
151
+ if (!classInfo) {
152
+ throw new Error(this.errorMessage('class info is undefined'));
446
153
  }
447
- return new WhileNode(condition, body);
448
- }
449
- parseThrowStatement() {
450
- this.consume(Token.THROW);
451
- if (this.scanner.hasLineTerminatorBeforeNext()) {
452
- throw new Error(this.scanner.createError(`New line After Throw`));
154
+ if (propInfo.position !== PropertyPosition.ClassLiteral) {
155
+ throw new Error(this.errorMessage('expected property position ClassLiteral'));
453
156
  }
454
- const exception = this.parseExpression();
455
- this.expectSemicolon();
456
- return new ThrowStatement(exception);
457
- }
458
- parseSwitchStatement() {
459
- this.consume(Token.SWITCH);
460
- this.expect(Token.L_PARENTHESES);
461
- const tag = this.parseExpression();
462
- this.expect(Token.R_PARENTHESES);
463
- const cases = [];
464
- const switchStatement = new SwitchStatement(tag, cases);
465
- let defaultSeen = false;
466
- this.expect(Token.L_CURLY);
467
- while (this.peek().isNotType(Token.R_CURLY)) {
468
- const statements = [];
469
- let label;
470
- if (this.check(Token.CASE)) {
471
- label = this.parseExpression();
157
+ const nameToken = this.peek();
158
+ let nameExpression;
159
+ if (nameToken.isType(Token.STATIC)) {
160
+ this.consume(Token.STATIC);
161
+ if (this.peek().isType(Token.LPAREN)) {
162
+ propInfo.kind = PropertyKind.Method;
163
+ nameExpression = this.parseIdentifier();
164
+ propInfo.name = nameExpression.getName();
472
165
  }
473
- else {
474
- this.expect(Token.DEFAULT);
475
- if (defaultSeen) {
476
- throw new Error(this.errorMessage(`Multiple Defaults In Switch`));
477
- }
478
- defaultSeen = true;
166
+ else if (this.peek().isType(Token.ASSIGN)
167
+ || this.peek().isType(Token.SEMICOLON)
168
+ || this.peek().isType(Token.RBRACK)) {
169
+ nameExpression = this.parseIdentifier();
170
+ propInfo.name = nameExpression.getName();
479
171
  }
480
- this.expect(Token.COLON);
481
- while (this.peek().isNotType(Token.CASE)
482
- && this.peek().isNotType(Token.DEFAULT)
483
- && this.peek().isNotType(Token.R_CURLY)) {
484
- const statement = this.parseStatementListItem();
485
- if (!statement || this.isEmptyStatement(statement)) {
486
- continue;
487
- }
488
- statements.push(statement);
172
+ else {
173
+ propInfo.isStatic = true;
174
+ nameExpression = this.parseProperty(propInfo);
489
175
  }
490
- const block = new BlockStatement(statements, true);
491
- const clause = defaultSeen ? new DefaultExpression(block) : new SwitchCase(label, block);
492
- cases.push(clause);
493
- }
494
- this.expect(Token.R_CURLY);
495
- return switchStatement;
496
- }
497
- parseForStatement() {
498
- this.consume(Token.FOR);
499
- const isAwait = this.check(Token.AWAIT);
500
- this.expect(Token.L_PARENTHESES);
501
- const peek = this.peek();
502
- const startsWithLet = peek.isType(Token.LET) || peek.isType(Token.VAR);
503
- let initializer;
504
- if (peek.isType(Token.CONST) || (startsWithLet && this.isNextLetKeyword())) {
505
- initializer = this.parseVariableDeclarations();
506
- }
507
- else if (peek.isType(Token.SEMICOLON)) {
508
- initializer = EmptyStatement.INSTANCE;
509
176
  }
510
177
  else {
511
- initializer = this.parseExpressionCoverGrammar();
178
+ nameExpression = this.parseProperty(propInfo);
512
179
  }
513
- if (initializer instanceof BinaryExpression) {
514
- const objectNode = initializer.getRight();
515
- initializer = initializer.getLeft();
516
- this.expect(Token.R_PARENTHESES);
517
- const statement = this.parseStatement();
518
- return new ForInNode(initializer, objectNode, statement);
519
- }
520
- const forMode = this.checkInOrOf();
521
- if (forMode) {
522
- const object = forMode === 'IN' ? this.parseAssignmentExpression() : this.parseExpression();
523
- this.expect(Token.R_PARENTHESES);
524
- const statement = this.parseStatement();
525
- if (statement instanceof BlockStatement) {
526
- statement.isStatement = true;
527
- }
528
- if (isAwait && forMode === 'OF') {
529
- return new ForAwaitOfNode(initializer, object, statement);
530
- }
531
- else if (forMode === 'OF') {
532
- return new ForOfNode(initializer, object, statement);
533
- }
534
- else if (forMode === 'IN') {
535
- return new ForInNode(initializer, object, statement);
536
- }
537
- else {
538
- throw new Error(this.errorMessage(`parsing for loop: ${this.position()}`));
180
+ switch (propInfo.kind) {
181
+ case PropertyKind.Assign:
182
+ case PropertyKind.ClassField:
183
+ case PropertyKind.ShorthandOrClassField:
184
+ case PropertyKind.NotSet: {
185
+ propInfo.kind = PropertyKind.ClassField;
186
+ const initializer = this.parseMemberInitializer(classInfo, propInfo.isStatic);
187
+ this.expectSemicolon();
188
+ const result = this.newClassLiteralProperty(nameExpression, initializer, ClassLiteralPropertyKind.FIELD, propInfo.isStatic, propInfo.isComputedName, propInfo.isPrivate);
189
+ this.setFunctionNameFromPropertyName(result, propInfo.name);
190
+ return result;
539
191
  }
540
- }
541
- this.expect(Token.SEMICOLON);
542
- let condition;
543
- if (!this.check(Token.SEMICOLON)) {
544
- condition = this.parseExpression();
545
- this.expect(Token.SEMICOLON);
546
- }
547
- let finalExpression;
548
- if (!this.check(Token.R_PARENTHESES)) {
549
- finalExpression = this.parseExpression();
550
- this.expect(Token.R_PARENTHESES);
551
- }
552
- const body = this.parseStatement();
553
- if (body instanceof BlockStatement) {
554
- body.isStatement = true;
555
- }
556
- return new ForNode(body, initializer, condition, finalExpression);
557
- }
558
- parseVariableDeclarations() {
559
- let mode;
560
- const token = this.peek().token;
561
- switch (token) {
562
- case Token.CONST:
563
- this.consume(token);
564
- mode = 'const';
565
- break;
566
- case Token.VAR:
567
- this.consume(token);
568
- mode = 'var';
569
- case Token.LET:
570
- default:
571
- this.consume(token);
572
- mode = 'let';
573
- break;
574
- }
575
- const variables = [];
576
- do {
577
- let name;
578
- let value;
579
- if (Token.isAnyIdentifier(this.peek().token)) {
580
- name = this.parseAndClassifyIdentifier(this.next());
581
- if (this.isEvalOrArguments(name)) {
582
- throw new Error(this.errorMessage(`Strict Eval Arguments`));
192
+ case PropertyKind.Method: {
193
+ if (!propInfo.isComputedName) {
194
+ this.checkClassMethodName(propInfo, classInfo);
583
195
  }
584
- }
585
- else {
586
- name = this.parseBindingPattern(true);
587
- }
588
- if (this.check(Token.ASSIGN)) {
589
- value = this.parseAssignmentExpression();
590
- }
591
- else if (!this.peekInOrOf()) {
592
- if (mode === 'const' && (name === undefined || value === undefined)) {
593
- throw new Error(this.errorMessage(`Declaration Missing Initializer : ${this.position()}`));
196
+ let kind = this.methodKindFor(propInfo.isStatic, propInfo.funcFlag);
197
+ if (!propInfo.isStatic && propInfo.name.toString() === 'constructor') {
198
+ classInfo.hasSeenConstructor = true;
199
+ kind = hasExtends ? FunctionKind.DerivedConstructor : FunctionKind.BaseConstructor;
594
200
  }
201
+ const value = this.parseFunctionLiteral(kind, FunctionSyntaxKind.AccessorOrMethod, nameExpression);
202
+ const result = this.newClassLiteralProperty(nameExpression, value, ClassLiteralProperty.Kind.METHOD, propInfo.isStatic, propInfo.isComputedName, propInfo.isPrivate);
203
+ this.setFunctionNameFromPropertyName(result, propInfo.name);
204
+ return result;
595
205
  }
596
- variables.push(new VariableNode(name, value));
597
- } while (this.check(Token.COMMA));
598
- return new VariableDeclarationNode(variables, mode);
599
- }
600
- parseBindingPattern(isPattern) {
601
- const token = this.peek().token;
602
- if (Token.isAnyIdentifier(token)) {
603
- const name = this.parseAndClassifyIdentifier(this.next());
604
- if (this.isEvalOrArguments(name)) {
605
- throw new Error(this.errorMessage(`Strict Eval Arguments`));
206
+ case PropertyKind.AccessorGetter:
207
+ case PropertyKind.AccessorSetter: {
208
+ if (propInfo.funcFlag !== ParseFunctionFlag.IsNormal) {
209
+ throw new Error(this.errorMessage('accessor is not normal function'));
210
+ }
211
+ const isGet = propInfo.kind == PropertyKind.AccessorGetter;
212
+ if (!propInfo.isComputedName) {
213
+ this.checkClassMethodName(propInfo, classInfo);
214
+ nameExpression = new Literal(propInfo.name);
215
+ }
216
+ let kind;
217
+ if (propInfo.isStatic) {
218
+ kind = isGet ? FunctionKind.StaticGetterFunction
219
+ : FunctionKind.StaticSetterFunction;
220
+ }
221
+ else {
222
+ kind = isGet ? FunctionKind.GetterFunction
223
+ : FunctionKind.SetterFunction;
224
+ }
225
+ const value = this.parseFunctionLiteral(kind, FunctionSyntaxKind.AccessorOrMethod, nameExpression);
226
+ const propertyKind = isGet ? ClassLiteralProperty.Kind.GETTER : ClassLiteralProperty.Kind.SETTER;
227
+ const result = this.newClassLiteralProperty(nameExpression, value, propertyKind, propInfo.isStatic, propInfo.isComputedName, propInfo.isPrivate);
228
+ const prefix = isGet ? 'get ' : 'set ';
229
+ this.setFunctionNameFromPropertyName(result, propInfo.name, prefix);
230
+ return result;
606
231
  }
607
- return name;
608
- }
609
- if (token == Token.L_BRACKETS) {
610
- return this.parseArrayLiteral(isPattern);
611
- }
612
- else if (token == Token.L_CURLY) {
613
- return this.parseObjectLiteral(isPattern);
614
- }
615
- else {
616
- throw new Error(this.errorMessage(`Unexpected Token: ${this.next().getValue()}`));
232
+ case PropertyKind.Value:
233
+ case PropertyKind.Shorthand:
234
+ case PropertyKind.Spread:
235
+ return NullNode;
617
236
  }
237
+ throw new Error(this.errorMessage('UNREACHABLE'));
618
238
  }
619
- parseAndClassifyIdentifier(next) {
620
- if (next.isType(Token.IDENTIFIER)) {
621
- return next.getValue();
239
+ checkClassMethodName(propInfo, classInfo) {
240
+ if (!(propInfo.kind == PropertyKind.Method || isAccessor(propInfo.kind))) {
241
+ throw new Error(this.errorMessage('not kind of method or setter or getter'));
622
242
  }
623
- else if (next.isType(Token.SET)) {
624
- const value = this.parseFunctionDeclaration();
625
- return new Property(next.getValue(), value, 'set');
243
+ if (propInfo.isPrivate && propInfo.name.toString() === 'constructor') {
244
+ throw new Error(this.errorMessage('constructor is private'));
626
245
  }
627
- else if (next.isType(Token.GET)) {
628
- const value = this.parseFunctionDeclaration();
629
- return new Property(next.getValue(), value, 'get');
246
+ else if (propInfo.isStatic && propInfo.name.toString() === 'prototype') {
247
+ throw new Error(this.errorMessage('static prototype'));
630
248
  }
631
- else if (next.isType(Token.AWAIT)) {
632
- throw new Error(this.errorMessage(`un supported expression (await)`));
249
+ else if (propInfo.name.toString() === 'constructor') {
250
+ if (propInfo.funcFlag !== ParseFunctionFlag.IsNormal || isAccessor(propInfo.kind)) {
251
+ if (propInfo.funcFlag === ParseFunctionFlag.IsGenerator) {
252
+ throw new Error(this.errorMessage('constructor is generator'));
253
+ }
254
+ else if (propInfo.funcFlag === ParseFunctionFlag.IsAsync) {
255
+ throw new Error(this.errorMessage('constructor is async'));
256
+ }
257
+ if (classInfo.hasSeenConstructor) {
258
+ throw new Error(this.errorMessage('duplicate constructor'));
259
+ }
260
+ }
261
+ classInfo.hasSeenConstructor = true;
633
262
  }
634
- return next.getValue();
635
263
  }
636
- parseContinueStatement() {
637
- this.consume(Token.CONTINUE);
638
- this.expectSemicolon();
639
- return ContinueStatement.CONTINUE_INSTANCE;
264
+ parseClassStaticBlock(classInfo) {
265
+ this.consume(Token.STATIC);
266
+ this.setStatue(true, FunctionKind.ClassStaticInitializerFunction);
267
+ const block = this.parseBlock();
268
+ this.restoreStatue();
269
+ classInfo.hasStaticElements = true;
270
+ return new StaticBlock(block.getBody());
640
271
  }
641
- parseBreakStatement() {
642
- this.consume(Token.BREAK);
643
- this.expectSemicolon();
644
- return BreakStatement.BREAK_INSTANCE;
272
+ declareClass(variableName, value, names) {
273
+ names?.push(variableName);
274
+ const proxy = this.declareVariable(variableName, 'let');
275
+ return new AssignmentExpression('=', proxy, value);
645
276
  }
646
- parseReturnStatement() {
647
- this.consume(Token.RETURN);
648
- const tokenExp = this.peek();
649
- let returnValue;
650
- if (this.scanner.hasLineTerminatorBeforeNext() || Token.isAutoSemicolon(tokenExp.token)) {
651
- }
652
- else {
653
- returnValue = this.parseExpression();
654
- }
655
- this.expectSemicolon();
656
- return new ReturnStatement(returnValue);
277
+ declareVariable(name, mode) {
278
+ return new VariableDeclarationNode([new VariableDeclarator(new Identifier(name))], mode);
657
279
  }
658
- parseExpressionOrLabelledStatement() {
659
- switch (this.peek().token) {
660
- case Token.FUNCTION:
661
- case Token.L_CURLY:
662
- throw new Error(this.errorMessage(`Unreachable state`));
663
- case Token.CLASS:
664
- throw new Error(this.errorMessage(`Unexpected Token ${this.next().getValue().toString()}`));
665
- case Token.LET: {
666
- const nextNext = this.peekAhead();
667
- if (nextNext.isNotType(Token.L_BRACKETS) &&
668
- ((nextNext.isNotType(Token.L_CURLY) && nextNext.isNotType(Token.IDENTIFIER)))) {
669
- break;
280
+ newClassLiteralProperty(nameExpression, initializer, kind, isStatic, isComputedName, isPrivate) {
281
+ switch (kind) {
282
+ case ClassLiteralPropertyKind.METHOD:
283
+ if (nameExpression.toString() === 'constructor') {
284
+ return new MethodDefinition('constructor', nameExpression, initializer, [], isComputedName, isStatic);
670
285
  }
671
- throw new Error(this.errorMessage(`Unexpected Lexical Declaration ${this.position()}`));
672
- }
286
+ return new MethodDefinition('method', nameExpression, initializer, [], isComputedName, isStatic);
287
+ case ClassLiteralPropertyKind.GETTER:
288
+ return new MethodDefinition('get', nameExpression, initializer, [], isComputedName, isStatic);
289
+ case ClassLiteralPropertyKind.SETTER:
290
+ return new MethodDefinition('set', nameExpression, initializer, [], isComputedName, isStatic);
291
+ case ClassLiteralPropertyKind.FIELD:
292
+ return new PropertyDefinition(nameExpression, [], isComputedName, isStatic, initializer);
673
293
  default:
674
294
  break;
675
295
  }
676
- const startsWithIdentifier = Token.isAnyIdentifier(this.peek().token);
677
- const expression = this.parseExpressionCoverGrammar();
678
- if (this.peek().isType(Token.COLON) && startsWithIdentifier && this.isIdentifier(expression)) {
679
- this.consume(Token.COLON);
680
- if (this.peek().isType(Token.FUNCTION)) {
681
- return this.parseFunctionDeclaration();
682
- }
683
- return this.parseStatement();
684
- }
685
- this.expectSemicolon();
686
- return expression;
687
- }
688
- parseExpression() {
689
- return this.parseExpressionCoverGrammar();
690
- }
691
- parseFunctionDeclaration() {
692
- this.consume(Token.FUNCTION);
693
- if (this.check(Token.MUL)) {
694
- throw new Error(this.errorMessage(`Error Generator In Single Statement Context`));
695
- }
696
- return this.parseHoistableDeclaration(FunctionKind.NORMAL);
697
- }
698
- parseFunctionDeclarationAndGenerator() {
699
- this.consume(Token.FUNCTION);
700
- if (this.check(Token.MUL)) {
701
- return this.parseHoistableDeclaration(FunctionKind.GENERATOR);
702
- }
703
- return this.parseHoistableDeclaration(FunctionKind.NORMAL);
296
+ throw new Error(this.errorMessage('UNREACHABLE'));
704
297
  }
705
- parseHoistableDeclaration(flag) {
706
- if (FunctionKind.ASYNC === flag && this.check(Token.MUL)) {
707
- flag = FunctionKind.ASYNC_GENERATOR;
298
+ parseMemberInitializer(classInfo, isStatic) {
299
+ const kind = isStatic
300
+ ? FunctionKind.ClassStaticInitializerFunction
301
+ : FunctionKind.ClassMembersInitializerFunction;
302
+ let initializer = undefined;
303
+ if (this.check(Token.ASSIGN)) {
304
+ this.setStatue(true, kind);
305
+ initializer = this.parseAssignmentExpression();
306
+ this.restoreStatue();
708
307
  }
709
- let name;
710
- if (this.peek().isNotType(Token.L_PARENTHESES)) {
711
- name = this.parseIdentifier();
308
+ if (isStatic) {
309
+ classInfo.hasStaticElements = true;
712
310
  }
713
- return this.parseFunctionLiteral(flag, name);
714
- }
715
- parseIdentifier() {
716
- const next = this.next();
717
- if (!Token.isValidIdentifier(next.token)) {
718
- throw new Error(this.errorMessage(`Unexpected Token: ${next.getValue()}`));
719
- }
720
- if (next.isType(Token.IDENTIFIER)) {
721
- return next.getValue();
311
+ else {
312
+ classInfo.hasInstanceMembers = true;
722
313
  }
723
- return this.getIdentifier();
314
+ return initializer;
724
315
  }
725
- getIdentifier() {
726
- const current = this.current();
727
- const string = current.getValue().toString();
728
- switch (current.token) {
729
- case Token.AWAIT:
730
- return AwaitIdentifier;
731
- case Token.ASYNC:
732
- return AsyncIdentifier;
733
- case Token.PRIVATE_NAME:
734
- return new Identifier(`#${string}`);
735
- default:
736
- break;
737
- }
738
- if (string == 'constructor') {
739
- return ConstructorIdentifier;
740
- }
741
- if (string == 'name') {
742
- return NameIdentifier;
743
- }
744
- if (string == 'eval') {
745
- return EvalIdentifier;
746
- }
747
- else if (string == 'arguments') {
748
- return ArgumentsIdentifier;
749
- }
750
- throw new Error(this.errorMessage(`can't identify token ${string}`));
316
+ setFunctionNameFromPropertyName(property, name, prefix) {
751
317
  }
752
- parseFunctionLiteral(flag, name) {
753
- const functionInfo = {};
754
- this.expect(Token.L_PARENTHESES);
755
- const formals = this.parseFormalParameterList(functionInfo);
756
- this.expect(Token.R_PARENTHESES);
757
- const body = this.parseFunctionBody();
758
- if (name) {
759
- return new FunctionDeclaration(formals, body, flag, name, functionInfo.rest);
318
+ parseSuperExpression() {
319
+ this.consume(Token.SUPER);
320
+ if (Token.isProperty(this.peek().token)) {
321
+ if (this.peek().isType(Token.PERIOD) && this.peekAhead().isType(Token.PRIVATE_NAME)) {
322
+ this.consume(Token.PERIOD);
323
+ this.consume(Token.PRIVATE_NAME);
324
+ throw new Error(this.errorMessage('Unexpected Private Field'));
325
+ }
326
+ if (this.peek().isType(Token.QUESTION_PERIOD)) {
327
+ this.consume(Token.QUESTION_PERIOD);
328
+ throw new Error(this.errorMessage('Optional Chaining No Super'));
329
+ }
330
+ return Super.INSTANCE;
760
331
  }
761
- return new FunctionExpression(formals, body, flag, name, functionInfo.rest);
332
+ throw new Error(this.errorMessage('Unexpected Super'));
762
333
  }
763
- parseArrowFunctionBody() {
764
- const isExpression = this.peek().isNotType(Token.L_CURLY);
765
- if (isExpression) {
766
- const expression = this.parseAssignmentExpression();
767
- return expression;
768
- }
769
- else {
770
- return this.parseFunctionBody();
334
+ rewriteClassLiteral(classInfo, name) {
335
+ const body = [];
336
+ if (classInfo.hasSeenConstructor) {
337
+ body.push(classInfo.constructor);
771
338
  }
339
+ body.push(...classInfo.staticElements);
340
+ body.push(...classInfo.instanceFields);
341
+ body.push(...classInfo.publicMembers);
342
+ body.push(...classInfo.privateMembers);
343
+ return new ClassBody(body);
772
344
  }
773
- parseFunctionBody() {
774
- this.expect(Token.L_CURLY);
775
- const list = this.parseStatementList(Token.R_CURLY);
776
- this.expect(Token.R_CURLY);
777
- return list;
778
- }
779
- parseStatementList(endToken) {
780
- const list = [];
781
- while (this.peek().isNotType(endToken)) {
782
- const stat = this.parseStatementListItem();
345
+ parseModuleItemList() {
346
+ const body = [];
347
+ while (this.peek().isNotType(Token.EOS)) {
348
+ const stat = this.parseModuleItem();
783
349
  if (!stat) {
784
350
  break;
785
351
  }
786
352
  if (this.isEmptyStatement(stat)) {
787
353
  continue;
788
354
  }
789
- list.push(stat);
790
- }
791
- return list;
792
- }
793
- parseFormalParameterList(functionInfo) {
794
- const parameters = [];
795
- if (this.peek().isNotType(Token.R_PARENTHESES)) {
796
- while (true) {
797
- const param = this.parseFormalParameter(functionInfo);
798
- parameters.push(param);
799
- if (functionInfo.rest) {
800
- if (this.peek().isType(Token.COMMA)) {
801
- throw new Error(this.errorMessage(`Param After Rest`));
802
- }
803
- break;
804
- }
805
- if (!this.check(Token.COMMA))
806
- break;
807
- if (this.peek().isType(Token.R_PARENTHESES)) {
808
- break;
809
- }
810
- }
355
+ body.push(stat);
811
356
  }
812
- return parameters;
357
+ return body;
813
358
  }
814
- parseFormalParameter(functionInfo) {
815
- functionInfo.rest = this.check(Token.ELLIPSIS);
816
- let pattern = this.parseBindingPattern(true);
817
- let initializer;
818
- if (this.check(Token.ASSIGN)) {
819
- if (functionInfo.rest) {
820
- throw new Error(this.errorMessage(`Rest Default Initializer`));
821
- }
822
- const value = this.parseAssignmentExpression();
823
- initializer = new Param(pattern, value);
824
- }
825
- else {
826
- initializer = new Param(pattern);
359
+ parseModuleItem() {
360
+ const next = this.peek();
361
+ if (next.isType(Token.EXPORT)) {
362
+ return this.parseExportDeclaration();
827
363
  }
828
- return initializer;
829
- }
830
- parseExpressionCoverGrammar(info) {
831
- let variableIndex = 0;
832
- const list = [];
833
- let expression;
834
- while (true) {
835
- if (this.peek().isType(Token.ELLIPSIS)) {
836
- if (info) {
837
- info.rest = true;
838
- }
839
- return this.parseArrowParametersWithRest(list, variableIndex);
840
- }
841
- expression = this.parseAssignmentExpressionCoverGrammar();
842
- list.push(expression);
843
- if (!this.check(Token.COMMA))
844
- break;
845
- if (this.peek().isType(Token.R_PARENTHESES) && this.peekAhead().isType(Token.ARROW)) {
846
- break;
364
+ if (next.isType(Token.IMPORT)) {
365
+ const peekAhead = this.peekAhead();
366
+ if (peekAhead.isNotType(Token.LPAREN) && peekAhead.isNotType(Token.PERIOD)) {
367
+ return this.parseImportDeclaration();
847
368
  }
848
369
  }
849
- if (list.length == 1)
850
- return expression;
851
- return this.expressionListToExpression(list);
370
+ return this.parseStatementListItem();
852
371
  }
853
- parseArrowParametersWithRest(list, variableIndex) {
854
- this.consume(Token.ELLIPSIS);
855
- const pattern = this.parseBindingPattern(true);
856
- if (this.peek().isType(Token.ASSIGN)) {
857
- throw new Error(this.errorMessage(`Error A rest parameter cannot have an initializer`));
858
- }
859
- if (this.peek().isType(Token.COMMA)) {
860
- throw new Error(this.errorMessage(`Error A rest parameter or binding pattern may not have a trailing comma`));
861
- }
862
- if (this.peek().isNotType(Token.R_PARENTHESES) || this.peekAhead().isNotType(Token.ARROW)) {
863
- throw new Error(this.errorMessage(`Error Unexpected Token At ${this.position()}`));
864
- }
865
- list.push(pattern);
866
- return this.expressionListToExpression(list);
867
- }
868
- expressionListToExpression(list) {
869
- if (list.length === 1) {
870
- return list[0];
871
- }
872
- return new SequenceExpression(list);
873
- }
874
- parseMemberExpression() {
875
- const result = this.parsePrimaryExpression();
876
- return this.parseMemberExpressionContinuation(result);
877
- }
878
- toParamNode(expression) {
879
- if (expression instanceof AssignmentExpression) {
880
- return new Param(expression.getLeft(), expression.getRight());
881
- }
882
- if (expression instanceof GroupingExpression) {
883
- return new Param(expression.getNode());
884
- }
885
- return new Param(expression);
886
- }
887
- parsePrimaryExpression() {
888
- let token = this.peek();
889
- if (Token.isAnyIdentifier(token.token)) {
890
- this.consume(token.token);
891
- let kind = ArrowFunctionType.NORMAL;
892
- if (token.isType(Token.ASYNC) && !this.scanner.hasLineTerminatorBeforeNext()) {
893
- if (this.peek().isType(Token.FUNCTION)) {
894
- return this.parseFunctionDeclarationAndGenerator();
895
- }
896
- ;
897
- if (Token.isAnyIdentifier(this.peek().token) && this.peekAhead().isType(Token.ARROW)) {
898
- token = this.next();
899
- kind = ArrowFunctionType.ASYNC;
900
- }
901
- }
902
- if (this.peek().isType(Token.ARROW)) {
903
- const name = this.parseAndClassifyIdentifier(token);
904
- const params = [];
905
- if (name instanceof SequenceExpression) {
906
- params.push(...name.getExpressions().map(this.toParamNode));
372
+ parseExportDeclaration() {
373
+ this.expect(Token.EXPORT);
374
+ let result;
375
+ const names = [];
376
+ switch (this.peek().token) {
377
+ case Token.DEFAULT:
378
+ return this.parseExportDefault();
379
+ case Token.MUL:
380
+ return this.parseExportStar();
381
+ case Token.LBRACE: {
382
+ const exportData = this.parseExportClause();
383
+ let moduleSpecifier;
384
+ let importAssertions;
385
+ if (this.checkContextualKeyword('from')) {
386
+ moduleSpecifier = this.parseModuleSpecifier();
387
+ importAssertions = this.parseImportAssertClause();
388
+ this.expectSemicolon();
907
389
  }
908
390
  else {
909
- params.push(this.toParamNode(name));
391
+ this.expectSemicolon();
910
392
  }
911
- return this.parseArrowFunctionLiteral(params, kind);
393
+ return new ExportNamedDeclaration(exportData, undefined, moduleSpecifier, importAssertions);
912
394
  }
913
- return this.parseAndClassifyIdentifier(token);
914
- }
915
- if (Token.isLiteral(token.token)) {
916
- return expressionFromLiteral(this.next());
917
- }
918
- switch (token.token) {
919
- case Token.NEW:
920
- return this.parseMemberWithPresentNewPrefixesExpression();
921
- case Token.THIS:
922
- this.consume(Token.THIS);
923
- return ThisNode;
924
- case Token.DIV:
925
- case Token.DIV_ASSIGN:
926
- return this.parseRegExpLiteral();
927
- case Token.FUNCTION:
928
- this.consume(Token.FUNCTION);
929
- if (this.peek().isType(Token.MUL)) {
930
- this.consume(Token.MUL);
931
- return this.parseFunctionExpression(FunctionKind.GENERATOR);
932
- }
933
- return this.parseFunctionExpression(FunctionKind.NORMAL);
934
- case Token.SUPER: {
935
- return this.parseSuperExpression();
936
- }
937
- case Token.IMPORT:
938
- return this.parseImportExpressions();
939
- case Token.L_BRACKETS:
940
- return this.parseArrayLiteral(false);
941
- case Token.L_CURLY:
942
- return this.parseObjectLiteral(false);
943
- case Token.L_PARENTHESES: {
944
- this.consume(Token.L_PARENTHESES);
945
- if (this.check(Token.R_PARENTHESES)) {
946
- if (!this.peek().isType(Token.ARROW)) {
947
- throw new Error(this.errorMessage(`Unexpected Token: ${Token.R_PARENTHESES.getName()}`));
948
- }
949
- return this.parseArrowFunctionLiteral([], ArrowFunctionType.NORMAL);
950
- }
951
- const peekToken = this.peek();
952
- let expression;
953
- const info = {};
954
- if (peekToken.isType(Token.FUNCTION)) {
955
- this.consume(Token.FUNCTION);
956
- expression = this.parseFunctionLiteral(FunctionKind.NORMAL);
957
- }
958
- else if (peekToken.isType(Token.ASYNC) && this.peekAhead().isType(Token.FUNCTION)) {
959
- this.consume(Token.ASYNC);
960
- this.consume(Token.FUNCTION);
961
- expression = this.parseFunctionLiteral(FunctionKind.ASYNC);
962
- }
963
- else {
964
- expression = this.parseExpressionCoverGrammar(info);
965
- }
966
- this.expect(Token.R_PARENTHESES);
967
- if (this.peek().isType(Token.ARROW)) {
968
- if (expression instanceof SequenceExpression) {
969
- expression = this.parseArrowFunctionLiteral(expression.getExpressions(), ArrowFunctionType.NORMAL, info.rest);
970
- }
971
- else {
972
- expression = this.parseArrowFunctionLiteral([expression], ArrowFunctionType.NORMAL, info.rest);
973
- }
974
- }
975
- return expression;
395
+ case Token.FUNCTION: {
396
+ const declaration = this.parseFunctionDeclaration();
397
+ const identifier = declaration.getId();
398
+ result = new ExportNamedDeclaration([new ExportSpecifier(identifier, identifier)], declaration);
399
+ break;
976
400
  }
977
401
  case Token.CLASS: {
978
402
  this.consume(Token.CLASS);
979
- let name;
980
- let isStrictReserved = false;
981
- if (this.peekAnyIdentifier()) {
982
- name = this.parseAndClassifyIdentifier(this.next());
983
- isStrictReserved = Token.isStrictReservedWord(this.current().token);
984
- }
985
- return this.parseClassLiteral(name, isStrictReserved);
403
+ const declaration = this.parseClassDeclaration(names, false);
404
+ const identifier = declaration.getId();
405
+ result = new ExportNamedDeclaration([new ExportSpecifier(identifier, identifier)], declaration);
406
+ break;
986
407
  }
987
- case Token.TEMPLATE_LITERALS:
988
- return this.parseTemplateLiteral();
989
- default:
408
+ case Token.VAR:
409
+ case Token.LET:
410
+ case Token.CONST:
411
+ const declaration = this.parseVariableStatement(VariableDeclarationContext.StatementListItem, names);
412
+ const specifiers = declaration.getDeclarations()
413
+ .map(node => new ExportSpecifier(node.getId(), node.getId()));
414
+ result = new ExportNamedDeclaration(specifiers, declaration);
990
415
  break;
416
+ case Token.ASYNC:
417
+ this.consume(Token.ASYNC);
418
+ if (this.peek().isType(Token.FUNCTION) && !this.scanner.hasLineTerminatorBeforeNext()) {
419
+ const declaration = this.parseAsyncFunctionDeclaration(names, false);
420
+ const identifier = declaration.getId();
421
+ result = new ExportNamedDeclaration([new ExportSpecifier(identifier, identifier)], declaration);
422
+ break;
423
+ }
424
+ default:
425
+ throw new SyntaxError(this.errorMessage('Unexpected Token'));
991
426
  }
992
- throw new Error(this.errorMessage(`Unexpected Token: ${JSON.stringify(this.next())}`));
993
- }
994
- parseTemplateLiteral(tag) {
995
- const template = this.next().getValue();
996
- const exprs = template.expressions.map(expr => JavaScriptParser.parse(expr));
997
- if (tag) {
998
- return new TaggedTemplateExpression(tag, template.strings, exprs);
999
- }
1000
- else {
1001
- return new TemplateLiteral(template.strings, exprs);
1002
- }
1003
- }
1004
- parseMemberWithPresentNewPrefixesExpression() {
1005
- this.consume(Token.NEW);
1006
- let classRef;
1007
- if (this.peek().isType(Token.IMPORT) && this.peekAhead().isType(Token.L_PARENTHESES)) {
1008
- throw new Error(this.errorMessage(`parsing new import (`));
1009
- }
1010
- else if (this.peek().isType(Token.SUPER)) {
1011
- throw new Error(this.errorMessage(`parsing new super() is never allowed`));
1012
- }
1013
- else if (this.peek().isType(Token.PERIOD)) {
1014
- classRef = this.parseNewTargetExpression();
1015
- return this.parseMemberExpressionContinuation(classRef);
1016
- }
1017
- else {
1018
- classRef = this.parseMemberExpression();
1019
- }
1020
- if (this.peek().isType(Token.L_PARENTHESES)) {
1021
- const args = this.parseArguments();
1022
- classRef = new NewExpression(classRef, args);
1023
- return this.parseMemberExpressionContinuation(classRef);
1024
- }
1025
- if (this.peek().isType(Token.QUESTION_PERIOD)) {
1026
- throw new Error(this.errorMessage(`parsing new xxx?.yyy at position`));
1027
- }
1028
- return new NewExpression(classRef);
427
+ return result;
1029
428
  }
1030
- parseArguments(maybeArrow) {
1031
- this.consume(Token.L_PARENTHESES);
1032
- const args = [];
1033
- while (this.peek().isNotType(Token.R_PARENTHESES)) {
1034
- const isSpread = this.check(Token.ELLIPSIS);
1035
- let argument = this.parseAssignmentExpressionCoverGrammar();
1036
- if (ParsingArrowHeadFlag.MaybeArrowHead === maybeArrow) {
1037
- if (isSpread) {
1038
- if (argument instanceof AssignmentExpression) {
1039
- throw new Error(this.errorMessage(` Rest parameter may not have a default initializer'`));
1040
- }
1041
- if (this.peek().isType(Token.COMMA)) {
1042
- throw new Error(this.errorMessage(`parsing '...spread,arg =>'`));
1043
- }
429
+ parseImportDeclaration() {
430
+ this.expect(Token.IMPORT);
431
+ const tok = this.peek();
432
+ if (tok.isType(Token.STRING)) {
433
+ const moduleSpecifier = this.parseModuleSpecifier();
434
+ const importAssertions = this.parseImportAssertClause();
435
+ this.expectSemicolon();
436
+ return new ImportDeclaration(moduleSpecifier, undefined, importAssertions);
437
+ }
438
+ let importDefaultBinding;
439
+ if (tok.isNotType(Token.MUL) && tok.isNotType(Token.LBRACE)) {
440
+ importDefaultBinding = this.parseNonRestrictedIdentifier();
441
+ }
442
+ let moduleNamespaceBinding;
443
+ let namedImports;
444
+ if (importDefaultBinding == undefined || this.check(Token.COMMA)) {
445
+ switch (this.peek().token) {
446
+ case Token.MUL: {
447
+ this.consume(Token.MUL);
448
+ this.expectContextualKeyword('as');
449
+ moduleNamespaceBinding = this.parseNonRestrictedIdentifier();
450
+ break;
1044
451
  }
452
+ case Token.LBRACE:
453
+ namedImports = this.parseNamedImports();
454
+ break;
455
+ default:
456
+ throw new SyntaxError(this.errorMessage('Unexpected Token'));
1045
457
  }
1046
- if (isSpread) {
1047
- argument = new SpreadElement(argument);
1048
- }
1049
- args.push(argument);
1050
- if (!this.check(Token.COMMA))
1051
- break;
1052
458
  }
1053
- if (!this.check(Token.R_PARENTHESES)) {
1054
- throw new Error(this.errorMessage(`parsing arguments call, expecting ')'`));
459
+ this.expectContextualKeyword('from');
460
+ const moduleSpecifier = this.parseModuleSpecifier();
461
+ const importAssertions = this.parseImportAssertClause();
462
+ this.expectSemicolon();
463
+ const specifiers = [];
464
+ if (moduleNamespaceBinding) {
465
+ specifiers.push(new ImportNamespaceSpecifier(moduleNamespaceBinding));
1055
466
  }
1056
- return args;
1057
- }
1058
- parseAssignmentExpressionCoverGrammar() {
1059
- if (this.peek().isType(Token.YIELD)) {
1060
- return this.parseYieldExpression();
467
+ if (importDefaultBinding) {
468
+ specifiers.push(new ImportDefaultSpecifier(importDefaultBinding));
1061
469
  }
1062
- let expression = this.parseConditionalExpression();
1063
- const op = this.peek().token;
1064
- if (!Token.isArrowOrAssignmentOp(op))
1065
- return expression;
1066
- if (op === Token.ARROW) {
1067
- if (!this.isIdentifier(expression) && !this.isParenthesized(expression)) {
1068
- throw new Error(this.errorMessage(`Malformed Arrow Fun Param List`));
1069
- }
1070
- if (expression instanceof SequenceExpression) {
1071
- const params = expression.getExpressions().map(expr => new Param(expr));
1072
- return this.parseArrowFunctionLiteral(params, ArrowFunctionType.NORMAL);
1073
- }
1074
- if (expression instanceof GroupingExpression) {
1075
- return this.parseArrowFunctionLiteral([new Param(expression.getNode())], ArrowFunctionType.NORMAL);
1076
- }
1077
- return this.parseArrowFunctionLiteral([new Param(expression)], ArrowFunctionType.NORMAL);
470
+ if (namedImports?.length) {
471
+ specifiers.push(...namedImports);
1078
472
  }
1079
- if (this.isAssignableIdentifier(expression)) {
1080
- if (this.isParenthesized(expression)) {
1081
- throw new Error(this.errorMessage(`Invalid Destructuring Target`));
1082
- }
473
+ return new ImportDeclaration(moduleSpecifier, specifiers.length ? specifiers : undefined, importAssertions);
474
+ }
475
+ parseImportExpressions() {
476
+ this.consume(Token.IMPORT);
477
+ if (this.check(Token.PERIOD)) {
478
+ this.expectContextualKeyword('meta');
479
+ return MetaProperty.ImportMeta;
1083
480
  }
1084
- else if (this.isProperty(expression)) {
481
+ if (this.peek().isNotType(Token.LPAREN)) {
482
+ throw new SyntaxError(this.errorMessage('Unexpected Token'));
1085
483
  }
1086
- else if (this.isPattern(expression) && Token.isAssignment(op)) {
1087
- if (this.isParenthesized(expression)) {
1088
- }
484
+ this.consume(Token.LPAREN);
485
+ if (this.peek().isType(Token.RPAREN)) {
486
+ throw new SyntaxError(this.errorMessage('Import Missing Specifier'));
1089
487
  }
1090
- else {
1091
- if (!this.isValidReferenceExpression(expression)) {
1092
- throw new Error(this.errorMessage(`Invalid Reference Expression`));
488
+ this.setAcceptIN(true);
489
+ const specifier = this.parseAssignmentExpressionCoverGrammar();
490
+ if (this.check(Token.COMMA)) {
491
+ if (this.check(Token.RPAREN)) {
492
+ return new ImportExpression(specifier);
1093
493
  }
1094
- if (Token.isLogicalAssignmentOp(op)) {
1095
- throw new Error(this.errorMessage(`Invalid Lhs In Assignment`));
494
+ else {
495
+ const importAssertions = this.parseAssignmentExpressionCoverGrammar();
496
+ this.check(Token.COMMA);
497
+ this.expect(Token.RPAREN);
498
+ return new ImportExpression(specifier, importAssertions);
1096
499
  }
1097
500
  }
1098
- this.consume(op);
1099
- const right = this.parseAssignmentExpression();
1100
- if (!Token.isAssignment(op)) {
1101
- throw new Error(this.errorMessage(`Invalid Destructuring Target`));
1102
- }
1103
- return new AssignmentExpression(op.getName(), expression, right);
1104
- }
1105
- parseAssignmentExpression() {
1106
- return this.parseAssignmentExpressionCoverGrammar();
501
+ this.expect(Token.RPAREN);
502
+ this.restoreAcceptIN();
503
+ return new ImportExpression(specifier);
1107
504
  }
1108
- parseArrowFunctionLiteral(parameters, flag, rest) {
1109
- this.consume(Token.ARROW);
1110
- const body = this.parseArrowFunctionBody();
1111
- return new ArrowFunctionExpression(parameters, body, flag, rest);
505
+ parseVariableStatement(varContext, names) {
506
+ const declarations = this.parseVariableDeclarations(varContext);
507
+ this.expectSemicolon();
508
+ names.push(...declarations.getDeclarations().map(d => d.getId().toString()));
509
+ return declarations;
1112
510
  }
1113
- parseRegExpLiteral() {
1114
- if (!this.scanner.scanRegExpPattern()) {
1115
- throw new Error('Unterminated RegExp');
511
+ parseImportAssertClause() {
512
+ if (this.scanner.hasLineTerminatorBeforeNext() || !this.checkContextualKeyword('assert')) {
513
+ return undefined;
1116
514
  }
1117
- return this.scanner.currentToken().getValue();
1118
- }
1119
- parseArrayLiteral(isPattern) {
1120
- this.consume(Token.L_BRACKETS);
1121
- const values = [];
1122
- let firstSpreadIndex = -1;
1123
- while (!this.check(Token.R_BRACKETS)) {
1124
- let elem;
1125
- if (this.peek().isType(Token.COMMA)) {
1126
- this.consume(Token.COMMA);
1127
- continue;
515
+ this.expect(Token.LBRACE);
516
+ const counts = {};
517
+ const importAssertions = [];
518
+ while (this.peek().isNotType(Token.RBRACE)) {
519
+ let attributeKey = this.checkAndGetValue(Token.STRING);
520
+ if (!attributeKey) {
521
+ attributeKey = this.parsePropertyOrPrivatePropertyName();
1128
522
  }
1129
- else if (this.check(Token.ELLIPSIS)) {
1130
- const argument = this.parsePossibleDestructuringSubPattern();
1131
- elem = isPattern
1132
- ? new RestElement(argument)
1133
- : new SpreadElement(argument);
1134
- if (firstSpreadIndex < 0) {
1135
- firstSpreadIndex = values.length;
1136
- }
1137
- if (this.peek().isType(Token.COMMA)) {
1138
- throw new Error(this.errorMessage(`Element After Rest @${this.position()}`));
1139
- }
523
+ this.expect(Token.COLON);
524
+ const attributeValue = this.expectAndGetValue(Token.STRING);
525
+ importAssertions.push(new ImportAttribute(attributeKey, attributeValue));
526
+ counts[attributeKey.toString()] = (counts[attributeKey.toString()] ?? 0) + 1;
527
+ if (counts[attributeKey.toString()] > 1) {
528
+ throw new SyntaxError(this.errorMessage('Import Assertion Duplicate Key'));
1140
529
  }
1141
- else {
1142
- elem = this.parsePossibleDestructuringSubPattern();
530
+ if (this.peek().isType(Token.RBRACE))
531
+ break;
532
+ if (!this.check(Token.COMMA)) {
533
+ throw new SyntaxError('Unexpected Token');
1143
534
  }
1144
- values.push(elem);
1145
- }
1146
- if (isPattern) {
1147
- return new ArrayPattern(values);
1148
535
  }
1149
- return new ArrayExpression(values);
536
+ this.expect(Token.RBRACE);
537
+ return importAssertions;
1150
538
  }
1151
- parsePossibleDestructuringSubPattern() {
1152
- return this.parseAssignmentExpressionCoverGrammar();
1153
- }
1154
- parseObjectLiteral(isPattern) {
1155
- this.consume(Token.L_CURLY);
1156
- const properties = [];
1157
- while (!this.check(Token.R_CURLY)) {
1158
- const property = this.parseObjectPropertyDefinition(isPattern);
1159
- properties.push(property);
1160
- if (this.peek().isNotType(Token.R_CURLY)) {
1161
- this.expect(Token.COMMA);
1162
- }
1163
- }
1164
- if (isPattern) {
1165
- return new ObjectPattern(properties);
1166
- }
1167
- return new ObjectExpression(properties);
539
+ parseModuleSpecifier() {
540
+ return this.expectAndGetValue(Token.STRING);
1168
541
  }
1169
- parseObjectPropertyDefinition(isPattern) {
1170
- const propInfo = { kind: PropertyKind.NotSet };
1171
- const nameExpression = this.parseProperty(propInfo);
1172
- switch (propInfo.kind) {
1173
- case PropertyKind.Spread:
1174
- let value = nameExpression;
1175
- if (isPattern) {
1176
- value = new RestElement(value.getArgument());
1177
- }
1178
- return new Property(value.getArgument(), value, 'init');
1179
- case PropertyKind.Value: {
1180
- this.consume(Token.COLON);
1181
- const value = this.parsePossibleDestructuringSubPattern();
1182
- return new Property(nameExpression, value, 'init');
1183
- }
1184
- case PropertyKind.Assign:
1185
- case PropertyKind.ShorthandOrClassField:
1186
- case PropertyKind.Shorthand: {
1187
- const lhs = new Identifier(propInfo.name);
1188
- if (!this.isAssignableIdentifier(lhs)) {
1189
- throw new Error(this.errorMessage('Strict Eval Arguments'));
1190
- }
1191
- let value;
1192
- if (this.peek().isType(Token.ASSIGN)) {
1193
- this.consume(Token.ASSIGN);
1194
- const rhs = this.parseAssignmentExpression();
1195
- value = new AssignmentExpression(Token.ASSIGN.getName(), lhs, rhs);
1196
- }
1197
- else {
1198
- value = lhs;
1199
- }
1200
- return new Property(nameExpression, value, 'init');
542
+ parseExportClause() {
543
+ this.expect(Token.LBRACE);
544
+ const exportData = [];
545
+ let nameTok = this.peek();
546
+ while (nameTok.isNotType(Token.RBRACE)) {
547
+ const localName = this.parseExportSpecifierName();
548
+ let exportName;
549
+ if (this.checkContextualKeyword('as')) {
550
+ exportName = this.parseExportSpecifierName();
1201
551
  }
1202
- case PropertyKind.Method: {
1203
- const value = this.parseFunctionLiteral(propInfo.funcFlag);
1204
- return new Property(nameExpression, value, 'init');
552
+ else {
553
+ exportName = localName;
1205
554
  }
1206
- case PropertyKind.AccessorGetter:
1207
- case PropertyKind.AccessorSetter: {
1208
- const isGet = propInfo.kind == PropertyKind.AccessorGetter;
1209
- const value = this.parseFunctionLiteral(propInfo.funcFlag);
1210
- return new Property(nameExpression, value, isGet ? 'get' : 'set');
555
+ exportData.push(new ExportSpecifier(exportName, localName));
556
+ if (this.peek().isType(Token.RBRACE))
557
+ break;
558
+ if (!this.check(Token.COMMA)) {
559
+ throw new SyntaxError('Unexpected Token');
1211
560
  }
1212
- case PropertyKind.ClassField:
1213
- case PropertyKind.NotSet:
1214
- return NullNode;
1215
561
  }
562
+ this.expect(Token.RBRACE);
563
+ return exportData;
1216
564
  }
1217
- parseProperty(propInfo) {
1218
- let nextToken = this.peek();
1219
- if (this.check(Token.ASYNC)) {
1220
- nextToken = this.peek();
1221
- if (nextToken.isNotType(Token.MUL)
1222
- && parsePropertyKindFromToken(nextToken.token, propInfo)
1223
- || this.scanner.hasLineTerminatorBeforeNext()) {
1224
- return AsyncIdentifier;
1225
- }
1226
- propInfo.kind = PropertyKind.Method;
1227
- propInfo.funcFlag = FunctionKind.ASYNC;
565
+ parseExportSpecifierName() {
566
+ const next = this.next();
567
+ if (next.isType(Token.IDENTIFIER) || Token.isPropertyName(next.token)) {
568
+ return next.getValue();
1228
569
  }
1229
- if (this.check(Token.MUL)) {
1230
- propInfo.kind = PropertyKind.Method;
1231
- propInfo.funcFlag = FunctionKind.ASYNC_GENERATOR;
570
+ if (next.isType(Token.STRING)) {
571
+ const exportName = next.getValue();
572
+ return exportName;
1232
573
  }
1233
- nextToken = this.peek();
1234
- if (propInfo.kind == PropertyKind.NotSet && nextToken.isType(Token.GET) || nextToken.isType(Token.SET)) {
1235
- const token = this.next();
1236
- if (parsePropertyKindFromToken(this.peek().token, propInfo)) {
1237
- return nextToken.isType(Token.GET) ? GetIdentifier : SetIdentifier;
574
+ throw new SyntaxError(this.errorMessage('Unexpected Token'));
575
+ }
576
+ parseNamedImports() {
577
+ this.expect(Token.LBRACE);
578
+ const result = [];
579
+ while (this.peek().isNotType(Token.RBRACE)) {
580
+ const importName = this.parseExportSpecifierName();
581
+ let localName = importName;
582
+ if (this.checkContextualKeyword('as')) {
583
+ localName = this.parsePropertyOrPrivatePropertyName();
1238
584
  }
1239
- if (token.isType(Token.GET)) {
1240
- propInfo.kind = PropertyKind.AccessorGetter;
585
+ if (!Token.isValidIdentifier(this.current().token, LanguageMode.Strict, false, isStrict(this.languageMode))) {
586
+ throw new SyntaxError(this.errorMessage('Unexpected Reserved Keyword'));
1241
587
  }
1242
- else if (token.isType(Token.SET)) {
1243
- propInfo.kind = PropertyKind.AccessorSetter;
588
+ else if (this.isEvalOrArguments(localName)) {
589
+ throw new SyntaxError(this.errorMessage('Strict Eval Arguments'));
1244
590
  }
1245
- }
1246
- let propertyName;
1247
- switch (nextToken.token) {
1248
- case Token.PRIVATE_NAME:
1249
- this.consume(Token.PRIVATE_NAME);
1250
- if (propInfo.kind == PropertyKind.NotSet) {
1251
- parsePropertyKindFromToken(this.peek().token, propInfo);
1252
- }
1253
- propertyName = this.getIdentifier();
1254
- break;
1255
- case Token.STRING:
1256
- case Token.NUMBER:
1257
- case Token.BIGINT:
1258
- this.consume(nextToken.token);
1259
- propertyName = nextToken.getValue();
1260
- propInfo.name = propertyName.getValue();
1261
- break;
1262
- case Token.L_BRACKETS:
1263
- this.consume(Token.L_BRACKETS);
1264
- propertyName = this.parseAssignmentExpression();
1265
- this.expect(Token.R_BRACKETS);
1266
- if (propInfo.kind === PropertyKind.NotSet) {
1267
- parsePropertyKindFromToken(this.peek().token, propInfo);
1268
- }
1269
- propInfo.name = propertyName.toString();
1270
- return propertyName;
1271
- case Token.ELLIPSIS:
1272
- if (propInfo.kind == PropertyKind.NotSet) {
1273
- this.consume(Token.ELLIPSIS);
1274
- propertyName = this.parsePossibleDestructuringSubPattern();
1275
- propInfo.kind = PropertyKind.Spread;
1276
- if (!this.isValidReferenceExpression(propertyName)) {
1277
- throw new Error(this.errorMessage('Invalid Rest Binding/Assignment Pattern'));
1278
- }
1279
- if (this.peek().isNotType(Token.R_CURLY)) {
1280
- throw new Error(this.errorMessage('Element After Rest'));
1281
- }
1282
- propInfo.name = propertyName.toString();
1283
- return propertyName;
1284
- }
1285
- default:
1286
- propertyName = new StringLiteral(this.parsePropertyName().toString());
1287
- propInfo.name = propertyName.toString();
591
+ result.push(new ImportSpecifier(localName, importName));
592
+ if (this.peek().isType(Token.RBRACE))
1288
593
  break;
594
+ this.expect(Token.COMMA);
1289
595
  }
1290
- if (propInfo.kind === PropertyKind.NotSet) {
1291
- parsePropertyKindFromToken(this.peek().token, propInfo);
1292
- }
1293
- return propertyName;
1294
- }
1295
- parseMemberExpressionContinuation(expression) {
1296
- if (!Token.isMember(this.peek().token))
1297
- return expression;
1298
- return this.doParseMemberExpressionContinuation(expression);
1299
- }
1300
- doParseMemberExpressionContinuation(expression) {
1301
- if (!Token.isMember(this.peek().token)) {
1302
- throw new Error(this.errorMessage(`Parsing member expression`));
1303
- }
1304
- do {
1305
- switch (this.peek().token) {
1306
- case Token.L_BRACKETS: {
1307
- this.consume(Token.L_BRACKETS);
1308
- const index = this.parseExpressionCoverGrammar();
1309
- expression = new MemberExpression(expression, index, true);
1310
- this.expect(Token.R_BRACKETS);
1311
- break;
1312
- }
1313
- case Token.PERIOD: {
1314
- this.consume(Token.PERIOD);
1315
- const key = this.parsePropertyName();
1316
- expression = new MemberExpression(expression, key, false);
1317
- break;
1318
- }
1319
- case Token.TEMPLATE_LITERALS: {
1320
- expression = this.parseTemplateLiteral(expression);
1321
- break;
1322
- }
1323
- default:
1324
- break;
1325
- }
1326
- } while (Token.isMember(this.peek().token));
1327
- return expression;
1328
- }
1329
- parsePropertyName() {
1330
- const next = this.next();
1331
- if (next.getValue() instanceof Identifier) {
1332
- return next.getValue();
1333
- }
1334
- if (Token.isPropertyName(next.token)) {
1335
- return new Identifier(next.token.getName());
1336
- }
1337
- throw new Error(this.errorMessage(`Parsing property expression: Unexpected Token`));
1338
- }
1339
- parsePipelineExpression(expression) {
1340
- let token;
1341
- while (Token.isPipelineOperator(token = this.peek().token)) {
1342
- this.consume(token);
1343
- expression = this.parsePipelineBody(expression);
1344
- }
1345
- return expression;
596
+ this.expect(Token.RBRACE);
597
+ return result;
1346
598
  }
1347
- parsePipelineBody(lhs) {
1348
- let body;
1349
- let token = this.peek();
1350
- switch (token.token) {
599
+ parseExportDefault() {
600
+ this.expect(Token.DEFAULT);
601
+ const localNames = [];
602
+ let result;
603
+ switch (this.peek().token) {
1351
604
  case Token.FUNCTION:
1352
- this.consume(Token.FUNCTION);
1353
- if (this.peek().isType(Token.MUL)) {
1354
- this.consume(Token.MUL);
1355
- body = this.parseFunctionExpression(FunctionKind.GENERATOR);
1356
- break;
1357
- }
1358
- body = this.parseFunctionExpression(FunctionKind.NORMAL);
605
+ result = this.parseHoistableDeclaration(localNames, true);
606
+ break;
607
+ case Token.CLASS:
608
+ this.consume(Token.CLASS);
609
+ result = this.parseClassDeclaration(localNames, true);
1359
610
  break;
1360
611
  case Token.ASYNC:
1361
- if (this.peekAhead().isType(Token.FUNCTION)) {
612
+ if (this.peekAhead().isType(Token.FUNCTION) && !this.scanner.hasLineTerminatorBeforeNext()) {
1362
613
  this.consume(Token.ASYNC);
1363
- this.consume(Token.FUNCTION);
1364
- if (this.peek().isType(Token.MUL)) {
1365
- this.consume(Token.MUL);
1366
- body = this.parseFunctionExpression(FunctionKind.ASYNC_GENERATOR);
1367
- break;
1368
- }
1369
- body = this.parseFunctionExpression(FunctionKind.ASYNC);
614
+ result = this.parseHoistableDeclaration(localNames, true);
1370
615
  break;
1371
616
  }
617
+ default: {
618
+ this.setAcceptIN(true);
619
+ result = this.parseAssignmentExpression();
620
+ this.expectSemicolon();
621
+ this.restoreAcceptIN();
1372
622
  break;
1373
- default:
1374
- break;
1375
- }
1376
- if (body) {
1377
- return new PipelineExpression(lhs, body);
1378
- }
1379
- if (token.isType(Token.L_PARENTHESES)) {
1380
- body = this.parsePrimaryExpression();
1381
- return new PipelineExpression(lhs, body);
1382
- }
1383
- const func = this.parseMemberExpression();
1384
- let args = [];
1385
- switch (this.peek().token) {
1386
- case Token.COLON:
1387
- do {
1388
- this.consume(Token.COLON);
1389
- const isSpread = this.check(Token.ELLIPSIS);
1390
- if (this.peek().isType(Token.CONDITIONAL)) {
1391
- this.consume(Token.CONDITIONAL);
1392
- if (isSpread) {
1393
- args.push('...?');
1394
- }
1395
- else {
1396
- args.push('?');
1397
- }
1398
- }
1399
- else {
1400
- const arg = this.parseAssignmentExpressionCoverGrammar();
1401
- if (isSpread) {
1402
- args.push(new SpreadElement(arg));
1403
- }
1404
- else {
1405
- args.push(arg);
1406
- }
1407
- }
1408
- } while (this.peek().isType(Token.COLON));
1409
- break;
1410
- case Token.L_PARENTHESES:
1411
- this.consume(Token.L_PARENTHESES);
1412
- let indexed = false;
1413
- while (this.peek().isNotType(Token.R_PARENTHESES)) {
1414
- const isSpread = this.check(Token.ELLIPSIS);
1415
- if (this.peek().isType(Token.CONDITIONAL)) {
1416
- this.consume(Token.CONDITIONAL);
1417
- indexed = true;
1418
- if (isSpread) {
1419
- args.push('...?');
1420
- }
1421
- else {
1422
- args.push('?');
1423
- }
1424
- }
1425
- else {
1426
- const arg = this.parseAssignmentExpressionCoverGrammar();
1427
- if (isSpread) {
1428
- args.push(new SpreadElement(arg));
1429
- }
1430
- else {
1431
- args.push(arg);
1432
- }
1433
- }
1434
- this.check(Token.COMMA);
1435
- }
1436
- this.expect(Token.R_PARENTHESES);
1437
- if (!indexed) {
1438
- body = new CallExpression(func, args);
1439
- return new PipelineExpression(lhs, body);
1440
- }
1441
- break;
1442
- default:
1443
- break;
1444
- }
1445
- return new PipelineExpression(lhs, func, args);
1446
- }
1447
- parseConditionalExpression() {
1448
- let expression = this.parseLogicalExpression();
1449
- expression = this.parsePipelineExpression(expression);
1450
- return this.peek().isType(Token.CONDITIONAL) ? this.parseConditionalContinuation(expression) : expression;
1451
- }
1452
- parseLogicalExpression() {
1453
- let expression = this.parseBinaryExpression(6);
1454
- const peek = this.peek();
1455
- if (peek.isType(Token.AND) || peek.isType(Token.OR)) {
1456
- const precedence = peek.token.getPrecedence();
1457
- expression = this.parseBinaryContinuation(expression, 4, precedence);
1458
- }
1459
- else if (peek.isType(Token.NULLISH)) {
1460
- expression = this.parseNullishExpression(expression);
1461
- }
1462
- return expression;
1463
- }
1464
- parseBinaryContinuation(x, prec, prec1) {
1465
- do {
1466
- while (this.peek().token.getPrecedence() === prec1) {
1467
- let y;
1468
- let op = this.next();
1469
- const is_right_associative = op.isType(Token.EXP);
1470
- const next_prec = is_right_associative ? prec1 : prec1 + 1;
1471
- y = this.parseBinaryExpression(next_prec);
1472
- if (Token.isCompare(op.token)) {
1473
- let cmp = op.token;
1474
- switch (op.token) {
1475
- case Token.NE:
1476
- cmp = Token.EQ;
1477
- break;
1478
- case Token.NE_STRICT:
1479
- cmp = Token.EQ_STRICT;
1480
- break;
1481
- default: break;
1482
- }
1483
- x = shortcutNumericLiteralBinaryExpression(x, y, cmp);
1484
- if (op.isNotType(cmp)) {
1485
- x = buildUnaryExpression(x, Token.NOT);
1486
- }
1487
- }
1488
- else {
1489
- x = shortcutNumericLiteralBinaryExpression(x, y, op.token);
1490
- }
1491
- }
1492
- --prec1;
1493
- } while (prec1 >= prec);
1494
- return x;
1495
- }
1496
- parseBinaryExpression(precedence) {
1497
- const x = this.parseUnaryExpression();
1498
- const precedence1 = this.peek().token.getPrecedence();
1499
- if (precedence1 >= precedence) {
1500
- return this.parseBinaryContinuation(x, precedence, precedence1);
1501
- }
1502
- return x;
1503
- }
1504
- parseUnaryExpression() {
1505
- const op = this.peek();
1506
- if (Token.isUnaryOrCount(op.token)) {
1507
- return this.parseUnaryOrPrefixExpression();
1508
- }
1509
- if (op.isType(Token.AWAIT)) {
1510
- return this.parseAwaitExpression();
1511
- }
1512
- return this.parsePostfixExpression();
1513
- }
1514
- parseUnaryOrPrefixExpression() {
1515
- const op = this.next();
1516
- const expression = this.parseUnaryExpression();
1517
- if (Token.isUnary(op.token)) {
1518
- if (op.isType(Token.DELETE)) {
1519
- if (this.isIdentifier(expression)) {
1520
- throw new Error(this.errorMessage(`"delete identifier" is a syntax error in strict mode`));
1521
- }
1522
- if (expression instanceof MemberExpression && expression.getProperty().toString().startsWith('#')) {
1523
- throw new Error(this.errorMessage(`"Delete Private Field" is a syntax error`));
1524
- }
1525
- }
1526
- if (this.peek().isType(Token.EXP)) {
1527
- throw new Error(this.errorMessage(`Unexpected Token Unary Exponentiation`));
1528
- }
1529
- }
1530
- if (Token.isCount(op.token) || Token.isUnary(op.token)) {
1531
- return buildUnaryExpression(expression, op.token);
1532
- }
1533
- throw new Error(this.errorMessage(`while rewrite unary operation`));
1534
- }
1535
- parsePostfixExpression() {
1536
- const expression = this.parseLeftHandSideExpression();
1537
- if (!Token.isCount(this.peek().token) || this.scanner.hasLineTerminatorBeforeNext()) {
1538
- return expression;
1539
- }
1540
- return this.parsePostfixContinuation(expression);
1541
- }
1542
- parsePostfixContinuation(expression) {
1543
- if (!this.isValidReferenceExpression(expression)) {
1544
- throw new Error(this.errorMessage(`Invalid LHS In Postfix Op.`));
1545
- }
1546
- const op = this.next();
1547
- return buildPostfixExpression(expression, op.token);
1548
- }
1549
- parseLeftHandSideExpression() {
1550
- const result = this.parseMemberExpression();
1551
- if (!Token.isPropertyOrCall(this.peek().token))
1552
- return result;
1553
- return this.parseLeftHandSideContinuation(result);
1554
- }
1555
- parseLeftHandSideContinuation(result) {
1556
- if (this.peek().isType(Token.L_PARENTHESES)
1557
- && this.isIdentifier(result)
1558
- && this.scanner.currentToken().isType(Token.ASYNC)
1559
- && !this.scanner.hasLineTerminatorBeforeNext()) {
1560
- const args = this.parseArguments(ParsingArrowHeadFlag.AsyncArrowFunction);
1561
- if (this.peek().isType(Token.ARROW)) {
1562
- if (!args.length)
1563
- return new EmptyStatement;
1564
- return this.expressionListToExpression(args);
1565
- }
1566
- result = new CallExpression(result, args);
1567
- if (!Token.isPropertyOrCall(this.peek().token))
1568
- return result;
1569
- }
1570
- let optionalChaining = false;
1571
- let isOptional = false;
1572
- do {
1573
- switch (this.peek().token) {
1574
- case Token.QUESTION_PERIOD: {
1575
- if (isOptional) {
1576
- throw new Error(this.errorMessage(`Failure Expression`));
1577
- }
1578
- this.consume(Token.QUESTION_PERIOD);
1579
- isOptional = true;
1580
- optionalChaining = true;
1581
- if (Token.isPropertyOrCall(this.peek().token))
1582
- continue;
1583
- const key = this.parsePropertyName();
1584
- result = new MemberExpression(result, key, false, isOptional);
1585
- break;
1586
- }
1587
- case Token.L_BRACKETS: {
1588
- this.consume(Token.L_BRACKETS);
1589
- const index = this.parseExpressionCoverGrammar();
1590
- result = new MemberExpression(result, index, true, isOptional);
1591
- this.expect(Token.R_BRACKETS);
1592
- break;
1593
- }
1594
- case Token.PERIOD: {
1595
- if (isOptional) {
1596
- throw new Error(this.errorMessage(`Unexpected Token:${this.position()}`));
1597
- }
1598
- this.consume(Token.PERIOD);
1599
- const key = this.parsePropertyName();
1600
- result = new MemberExpression(result, key, false, isOptional);
1601
- break;
1602
- }
1603
- case Token.L_PARENTHESES: {
1604
- const args = this.parseArguments();
1605
- if (result.toString() === 'eval') {
1606
- throw new Error(this.errorMessage(`'eval(...)' is not supported.`));
1607
- }
1608
- result = new CallExpression(result, args, isOptional);
1609
- break;
1610
- }
1611
- case Token.BIND: {
1612
- if (isOptional) {
1613
- throw new Error(this.errorMessage(`Unexpected Token:${this.position()}`));
1614
- }
1615
- this.consume(Token.BIND);
1616
- const key = this.parsePropertyName();
1617
- result = new BindExpression(result, key, false, isOptional);
1618
- break;
1619
- }
1620
- case Token.QUESTION_BIND: {
1621
- if (isOptional) {
1622
- throw new Error(this.errorMessage(`Failure Expression`));
1623
- }
1624
- this.consume(Token.QUESTION_BIND);
1625
- isOptional = true;
1626
- optionalChaining = true;
1627
- const key = this.parsePropertyName();
1628
- result = new BindExpression(result, key, true, isOptional);
1629
- break;
1630
- }
1631
- default:
1632
- if (optionalChaining) {
1633
- throw new Error(this.errorMessage(`Optional Chaining No Template support`));
1634
- }
1635
- result = this.parseTemplateLiteral(result);
1636
- break;
1637
- }
1638
- if (isOptional) {
1639
- isOptional = false;
1640
623
  }
1641
- } while (Token.isPropertyOrCall(this.peek().token));
1642
- if (optionalChaining) {
1643
- result = new ChainExpression(result);
1644
624
  }
1645
- return result;
1646
- }
1647
- parseAwaitExpression() {
1648
- this.consume(Token.AWAIT);
1649
- const value = this.parseUnaryExpression();
1650
- if (this.peek().isType(Token.EXP)) {
1651
- throw new Error(this.scanner.createError(`Unexpected Token Unary Exponentiation`));
1652
- }
1653
- return buildUnaryExpression(value, Token.AWAIT);
625
+ return new ExportDefaultDeclaration(result);
1654
626
  }
1655
- parseNullishExpression(expression) {
1656
- const list = [];
1657
- list.push(expression);
1658
- while (this.peek().isType(Token.NULLISH)) {
1659
- this.consume(Token.NULLISH);
1660
- expression = this.parseBinaryExpression(6);
1661
- list.push(expression);
1662
- }
1663
- expression = list.pop();
1664
- expression = list.reverse()
1665
- .reduce((previous, current) => new LogicalExpression(Token.NULLISH.getName(), current, previous), expression);
1666
- return expression;
1667
- }
1668
- parseConditionalContinuation(expression) {
1669
- this.consume(Token.CONDITIONAL);
1670
- const left = this.parseAssignmentExpression();
1671
- this.expect(Token.COLON);
1672
- const right = this.parseAssignmentExpression();
1673
- return new ConditionalExpression(expression, left, right);
1674
- }
1675
- parseYieldExpression() {
1676
- this.consume(Token.YIELD);
1677
- let delegating = false;
1678
- let expression;
1679
- if (this.check(Token.MUL)) {
1680
- delegating = true;
1681
- }
1682
- switch (this.peek().token) {
1683
- case Token.EOS:
1684
- case Token.SEMICOLON:
1685
- case Token.R_CURLY:
1686
- case Token.R_BRACKETS:
1687
- case Token.R_PARENTHESES:
1688
- case Token.COLON:
1689
- case Token.COMMA:
1690
- case Token.IN:
1691
- if (!delegating)
1692
- break;
1693
- throw new Error(this.errorMessage(`Delegating yields require an RHS`));
1694
- default:
1695
- expression = this.parseAssignmentExpressionCoverGrammar();
1696
- break;
627
+ parseExportStar() {
628
+ this.consume(Token.MUL);
629
+ if (!this.peekContextualKeyword('as')) {
630
+ this.expectContextualKeyword('from');
631
+ const moduleSpecifier = this.parseModuleSpecifier();
632
+ const importAssertions = this.parseImportAssertClause();
633
+ this.expectSemicolon();
634
+ return new ExportAllDeclaration(moduleSpecifier, undefined, importAssertions);
1697
635
  }
1698
- return new YieldExpression(delegating, expression);
1699
- }
1700
- parseNewTargetExpression() {
1701
- throw new Error(this.errorMessage('Expression (new.target) not supported.'));
1702
- }
1703
- parseClassDeclaration(names, defaultExport) {
1704
- throw new Error(this.errorMessage(`Expression (class) not supported.`));
1705
- }
1706
- parseClassLiteral(name, isStrictReserved) {
1707
- throw new Error(this.errorMessage(`Expression (class) not supported.`));
1708
- }
1709
- parseSuperExpression() {
1710
- throw new Error(this.errorMessage('Expression (supper) not supported.'));
1711
- }
1712
- parseImportExpressions() {
1713
- throw new Error(this.errorMessage('Expression (import) not supported.'));
636
+ this.expectContextualKeyword('as');
637
+ const exportName = this.parseExportSpecifierName();
638
+ this.expectContextualKeyword('from');
639
+ const moduleSpecifier = this.parseModuleSpecifier();
640
+ const importAssertions = this.parseImportAssertClause();
641
+ this.expectSemicolon();
642
+ return new ExportAllDeclaration(moduleSpecifier, exportName, importAssertions);
1714
643
  }
1715
644
  }
1716
645
  //# sourceMappingURL=parser.js.map