ripple 0.2.182 → 0.2.184
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.
- package/package.json +4 -2
- package/src/compiler/errors.js +3 -1
- package/src/compiler/index.d.ts +2 -1
- package/src/compiler/phases/1-parse/index.js +525 -311
- package/src/compiler/phases/1-parse/style.js +3 -1
- package/src/compiler/phases/2-analyze/css-analyze.js +116 -97
- package/src/compiler/phases/2-analyze/index.js +81 -51
- package/src/compiler/phases/2-analyze/prune.js +200 -58
- package/src/compiler/phases/2-analyze/validation.js +9 -7
- package/src/compiler/phases/3-transform/client/index.js +871 -394
- package/src/compiler/phases/3-transform/segments.js +99 -53
- package/src/compiler/phases/3-transform/server/index.js +278 -121
- package/src/compiler/scope.js +51 -104
- package/src/compiler/types/index.d.ts +834 -197
- package/src/compiler/types/parse.d.ts +1668 -0
- package/src/compiler/utils.js +62 -74
- package/src/utils/ast.js +247 -192
- package/src/utils/builders.js +309 -247
- package/src/utils/sanitize_template_string.js +2 -2
|
@@ -0,0 +1,1668 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Type definitions for Ripple's extended Acorn parser
|
|
3
|
+
*
|
|
4
|
+
* These types cover internal properties and static class members that aren't
|
|
5
|
+
* included in Acorn's official type definitions but are used by Ripple's parser.
|
|
6
|
+
*
|
|
7
|
+
* Based on acorn source code: https://github.com/acornjs/acorn
|
|
8
|
+
* and @sveltejs/acorn-typescript: https://github.com/sveltejs/acorn-typescript
|
|
9
|
+
*
|
|
10
|
+
* Usage in JSDoc: @type {Parse.Parser}
|
|
11
|
+
*/
|
|
12
|
+
|
|
13
|
+
import type * as acorn from 'acorn';
|
|
14
|
+
import type * as AST from 'estree';
|
|
15
|
+
import type * as ESTreeJSX from 'estree-jsx';
|
|
16
|
+
|
|
17
|
+
type ForInit = boolean | 'await';
|
|
18
|
+
|
|
19
|
+
declare module 'acorn' {
|
|
20
|
+
// Helper type for readToken method
|
|
21
|
+
type ReadToken = Parse.Parser['readToken'];
|
|
22
|
+
|
|
23
|
+
const tokContexts: Parse.TokContexts;
|
|
24
|
+
class Position implements AST.Position {
|
|
25
|
+
line: number;
|
|
26
|
+
column: number;
|
|
27
|
+
constructor(line: number, column: number);
|
|
28
|
+
}
|
|
29
|
+
function isNewLine(code: number): boolean;
|
|
30
|
+
|
|
31
|
+
interface Parser {
|
|
32
|
+
readToken(...args: Parameters<ReadToken>): ReturnType<ReadToken>;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
export namespace Parse {
|
|
37
|
+
/**
|
|
38
|
+
* Destructuring errors object used during expression parsing
|
|
39
|
+
* See: https://github.com/acornjs/acorn/blob/main/acorn/src/parseutil.js
|
|
40
|
+
*/
|
|
41
|
+
export interface DestructuringErrors {
|
|
42
|
+
shorthandAssign: number;
|
|
43
|
+
trailingComma: number;
|
|
44
|
+
parenthesizedAssign: number;
|
|
45
|
+
parenthesizedBind: number;
|
|
46
|
+
doubleProto: number;
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Binding type constants used in checkLVal* and declareName
|
|
51
|
+
* to determine the type of a binding
|
|
52
|
+
*/
|
|
53
|
+
export interface BindingType {
|
|
54
|
+
/** Not a binding */
|
|
55
|
+
BIND_NONE: 0;
|
|
56
|
+
/** Var-style binding */
|
|
57
|
+
BIND_VAR: 1;
|
|
58
|
+
/** Let- or const-style binding */
|
|
59
|
+
BIND_LEXICAL: 2;
|
|
60
|
+
/** Function declaration */
|
|
61
|
+
BIND_FUNCTION: 3;
|
|
62
|
+
/** Simple (identifier pattern) catch binding */
|
|
63
|
+
BIND_SIMPLE_CATCH: 4;
|
|
64
|
+
/** Special case for function names as bound inside the function */
|
|
65
|
+
BIND_OUTSIDE: 5;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* Branch ID for tracking disjunction structure in regular expressions
|
|
70
|
+
* Used to determine whether a duplicate capture group name is allowed
|
|
71
|
+
* because it is in a separate branch.
|
|
72
|
+
*/
|
|
73
|
+
export interface BranchID {
|
|
74
|
+
/** Parent disjunction branch */
|
|
75
|
+
parent: BranchID | null;
|
|
76
|
+
/** Identifies this set of sibling branches */
|
|
77
|
+
base: BranchID;
|
|
78
|
+
/** Check if this branch is separated from another branch */
|
|
79
|
+
separatedFrom(alt: BranchID): boolean;
|
|
80
|
+
/** Create a sibling branch */
|
|
81
|
+
sibling(): BranchID;
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* Regular expression validation state
|
|
86
|
+
* Used by the parser to validate regular expression literals
|
|
87
|
+
* See: https://github.com/acornjs/acorn/blob/main/acorn/src/regexp.js
|
|
88
|
+
*/
|
|
89
|
+
export interface RegExpValidationState {
|
|
90
|
+
/** Reference to the parser instance */
|
|
91
|
+
parser: Parser;
|
|
92
|
+
/** Valid flags for the current ECMAScript version */
|
|
93
|
+
validFlags: string;
|
|
94
|
+
/** Unicode properties data for the current ECMAScript version */
|
|
95
|
+
unicodeProperties: any;
|
|
96
|
+
/** Source pattern string of the regular expression */
|
|
97
|
+
source: string;
|
|
98
|
+
/** Flags string of the regular expression */
|
|
99
|
+
flags: string;
|
|
100
|
+
/** Start position of the regular expression in the source */
|
|
101
|
+
start: number;
|
|
102
|
+
/** Whether unicode flag (u) is enabled */
|
|
103
|
+
switchU: boolean;
|
|
104
|
+
/** Whether unicode sets flag (v) is enabled (ES2024+) */
|
|
105
|
+
switchV: boolean;
|
|
106
|
+
/** Whether named capture groups are enabled */
|
|
107
|
+
switchN: boolean;
|
|
108
|
+
/** Current position in the pattern */
|
|
109
|
+
pos: number;
|
|
110
|
+
/** Last integer value parsed */
|
|
111
|
+
lastIntValue: number;
|
|
112
|
+
/** Last string value parsed */
|
|
113
|
+
lastStringValue: string;
|
|
114
|
+
/** Whether the last assertion can be quantified */
|
|
115
|
+
lastAssertionIsQuantifiable: boolean;
|
|
116
|
+
/** Number of capturing parentheses */
|
|
117
|
+
numCapturingParens: number;
|
|
118
|
+
/** Maximum back reference number */
|
|
119
|
+
maxBackReference: number;
|
|
120
|
+
/** Map of group names to their information */
|
|
121
|
+
groupNames: Record<string, BranchID[]>;
|
|
122
|
+
/** Array of back reference names */
|
|
123
|
+
backReferenceNames: string[];
|
|
124
|
+
/** Current branch ID for tracking disjunction structure */
|
|
125
|
+
branchID: BranchID | null;
|
|
126
|
+
|
|
127
|
+
/** Reset state for a new pattern */
|
|
128
|
+
reset(start: number, pattern: string, flags: string): void;
|
|
129
|
+
/** Raise a validation error */
|
|
130
|
+
raise(message: string): void;
|
|
131
|
+
/** Get code point at position i (handles surrogate pairs if unicode mode) */
|
|
132
|
+
at(i: number, forceU?: boolean): number;
|
|
133
|
+
/** Get next index after position i (handles surrogate pairs if unicode mode) */
|
|
134
|
+
nextIndex(i: number, forceU?: boolean): number;
|
|
135
|
+
/** Get code point at current position */
|
|
136
|
+
current(forceU?: boolean): number;
|
|
137
|
+
/** Get code point at next position */
|
|
138
|
+
lookahead(forceU?: boolean): number;
|
|
139
|
+
/** Advance position to next character */
|
|
140
|
+
advance(forceU?: boolean): void;
|
|
141
|
+
/** Try to eat a specific character */
|
|
142
|
+
eat(ch: number, forceU?: boolean): boolean;
|
|
143
|
+
/** Try to eat a sequence of characters */
|
|
144
|
+
eatChars(chs: number[], forceU?: boolean): boolean;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
export interface Options extends Omit<acorn.Options, 'onComment' | 'ecmaVersion'> {
|
|
148
|
+
rippleOptions: {
|
|
149
|
+
loose: boolean;
|
|
150
|
+
};
|
|
151
|
+
// The type has "latest" but it's converted to 1e8 at runtime
|
|
152
|
+
// and if (ecmaVersion >= 2015) { ecmaVersion -= 2009 }
|
|
153
|
+
// so we're making it always a number to reflect the runtime values
|
|
154
|
+
ecmaVersion: number;
|
|
155
|
+
onComment(
|
|
156
|
+
block: boolean,
|
|
157
|
+
value: string,
|
|
158
|
+
start: number,
|
|
159
|
+
end: number,
|
|
160
|
+
start_loc: AST.Position,
|
|
161
|
+
end_loc: AST.Position,
|
|
162
|
+
metadata?: CommentMetaData | null,
|
|
163
|
+
): void;
|
|
164
|
+
}
|
|
165
|
+
|
|
166
|
+
export interface CommentMetaData {
|
|
167
|
+
containerId: number;
|
|
168
|
+
childIndex: number;
|
|
169
|
+
beforeMeaningfulChild: boolean;
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
/**
|
|
173
|
+
* Token context - controls how tokens are interpreted in different syntactic contexts
|
|
174
|
+
*/
|
|
175
|
+
export interface TokContext {
|
|
176
|
+
token: string;
|
|
177
|
+
isExpr: boolean;
|
|
178
|
+
preserveSpace?: boolean;
|
|
179
|
+
override?: ((parser: Parser) => acorn.Token) | null;
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
/**
|
|
183
|
+
* Token type definition
|
|
184
|
+
*/
|
|
185
|
+
export interface TokenType {
|
|
186
|
+
label: string;
|
|
187
|
+
keyword: string | undefined;
|
|
188
|
+
beforeExpr?: boolean;
|
|
189
|
+
startsExpr?: boolean;
|
|
190
|
+
isLoop?: boolean;
|
|
191
|
+
isAssign?: boolean;
|
|
192
|
+
prefix?: boolean;
|
|
193
|
+
postfix?: boolean;
|
|
194
|
+
binop?: number | null;
|
|
195
|
+
updateContext?: ((prevType: TokenType) => void) | null;
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
/**
|
|
199
|
+
* Acorn's built-in token contexts
|
|
200
|
+
*/
|
|
201
|
+
export interface TokContexts {
|
|
202
|
+
/** Block statement context - `{` in statement position */
|
|
203
|
+
b_stat: TokContext & { token: '{' };
|
|
204
|
+
/** Block expression context - `{` in expression position (object literals) */
|
|
205
|
+
b_expr: TokContext & { token: '{' };
|
|
206
|
+
/** Template literal context - `${` inside template */
|
|
207
|
+
b_tmpl: TokContext & { token: '${' };
|
|
208
|
+
/** Parenthesized statement context - `(` in statement position */
|
|
209
|
+
p_stat: TokContext & { token: '(' };
|
|
210
|
+
/** Parenthesized expression context - `(` in expression position */
|
|
211
|
+
p_expr: TokContext & { token: '(' };
|
|
212
|
+
/** Quasi/template context - `` ` `` backtick */
|
|
213
|
+
q_tmpl: TokContext & { token: '`' };
|
|
214
|
+
/** Function statement context - `function` keyword in statement */
|
|
215
|
+
f_stat: TokContext & { token: 'function' };
|
|
216
|
+
/** Function expression context - `function` keyword in expression */
|
|
217
|
+
f_expr: TokContext & { token: 'function' };
|
|
218
|
+
/** Generator function expression context - `function*` in expression */
|
|
219
|
+
f_expr_gen: TokContext & { token: 'function' };
|
|
220
|
+
/** Generator function context - `function*` in statement */
|
|
221
|
+
f_gen: TokContext & { token: 'function' };
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
/**
|
|
225
|
+
* Acorn's built-in token types
|
|
226
|
+
*/
|
|
227
|
+
export interface TokTypes {
|
|
228
|
+
// Literal tokens
|
|
229
|
+
num: TokenType & { label: 'num' };
|
|
230
|
+
regexp: TokenType & { label: 'regexp' };
|
|
231
|
+
string: TokenType & { label: 'string' };
|
|
232
|
+
name: TokenType & { label: 'name' };
|
|
233
|
+
privateId: TokenType & { label: 'privateId' };
|
|
234
|
+
eof: TokenType & { label: 'eof' };
|
|
235
|
+
|
|
236
|
+
// Punctuation tokens
|
|
237
|
+
bracketL: TokenType & { label: '[' };
|
|
238
|
+
bracketR: TokenType & { label: ']' };
|
|
239
|
+
braceL: TokenType & { label: '{' };
|
|
240
|
+
braceR: TokenType & { label: '}' };
|
|
241
|
+
parenL: TokenType & { label: '(' };
|
|
242
|
+
parenR: TokenType & { label: ')' };
|
|
243
|
+
comma: TokenType & { label: ',' };
|
|
244
|
+
semi: TokenType & { label: ';' };
|
|
245
|
+
colon: TokenType & { label: ':' };
|
|
246
|
+
dot: TokenType & { label: '.' };
|
|
247
|
+
question: TokenType & { label: '?' };
|
|
248
|
+
questionDot: TokenType & { label: '?.' };
|
|
249
|
+
arrow: TokenType & { label: '=>' };
|
|
250
|
+
template: TokenType & { label: 'template' };
|
|
251
|
+
invalidTemplate: TokenType & { label: 'invalidTemplate' };
|
|
252
|
+
ellipsis: TokenType & { label: '...' };
|
|
253
|
+
backQuote: TokenType & { label: '`' };
|
|
254
|
+
dollarBraceL: TokenType & { label: '${' };
|
|
255
|
+
|
|
256
|
+
// Operators
|
|
257
|
+
eq: TokenType & { label: '='; isAssign: true };
|
|
258
|
+
assign: TokenType & { label: '_='; isAssign: true };
|
|
259
|
+
incDec: TokenType & { label: '++/--'; prefix: true; postfix: true };
|
|
260
|
+
prefix: TokenType & { label: '!/~'; prefix: true };
|
|
261
|
+
logicalOR: TokenType & { label: '||'; binop: 1 };
|
|
262
|
+
logicalAND: TokenType & { label: '&&'; binop: 2 };
|
|
263
|
+
bitwiseOR: TokenType & { label: '|'; binop: 3 };
|
|
264
|
+
bitwiseXOR: TokenType & { label: '^'; binop: 4 };
|
|
265
|
+
bitwiseAND: TokenType & { label: '&'; binop: 5 };
|
|
266
|
+
equality: TokenType & { label: '==/!=/===/!=='; binop: 6 };
|
|
267
|
+
relational: TokenType & { label: '</>/<=/>='; binop: 7 };
|
|
268
|
+
bitShift: TokenType & { label: '<</>>/>>>'; binop: 8 };
|
|
269
|
+
plusMin: TokenType & { label: '+/-'; binop: 9; prefix: true };
|
|
270
|
+
modulo: TokenType & { label: '%'; binop: 10 };
|
|
271
|
+
star: TokenType & { label: '*'; binop: 10 };
|
|
272
|
+
slash: TokenType & { label: '/'; binop: 10 };
|
|
273
|
+
starstar: TokenType & { label: '**' };
|
|
274
|
+
coalesce: TokenType & { label: '??'; binop: 1 };
|
|
275
|
+
|
|
276
|
+
// Keywords (label matches keyword name)
|
|
277
|
+
_break: TokenType & { label: 'break'; keyword: 'break' };
|
|
278
|
+
_case: TokenType & { label: 'case'; keyword: 'case' };
|
|
279
|
+
_catch: TokenType & { label: 'catch'; keyword: 'catch' };
|
|
280
|
+
_continue: TokenType & { label: 'continue'; keyword: 'continue' };
|
|
281
|
+
_debugger: TokenType & { label: 'debugger'; keyword: 'debugger' };
|
|
282
|
+
_default: TokenType & { label: 'default'; keyword: 'default' };
|
|
283
|
+
_do: TokenType & { label: 'do'; keyword: 'do'; isLoop: true };
|
|
284
|
+
_else: TokenType & { label: 'else'; keyword: 'else' };
|
|
285
|
+
_finally: TokenType & { label: 'finally'; keyword: 'finally' };
|
|
286
|
+
_for: TokenType & { label: 'for'; keyword: 'for'; isLoop: true };
|
|
287
|
+
_function: TokenType & { label: 'function'; keyword: 'function' };
|
|
288
|
+
_if: TokenType & { label: 'if'; keyword: 'if' };
|
|
289
|
+
_return: TokenType & { label: 'return'; keyword: 'return' };
|
|
290
|
+
_switch: TokenType & { label: 'switch'; keyword: 'switch' };
|
|
291
|
+
_throw: TokenType & { label: 'throw'; keyword: 'throw' };
|
|
292
|
+
_try: TokenType & { label: 'try'; keyword: 'try' };
|
|
293
|
+
_var: TokenType & { label: 'var'; keyword: 'var' };
|
|
294
|
+
_const: TokenType & { label: 'const'; keyword: 'const' };
|
|
295
|
+
_while: TokenType & { label: 'while'; keyword: 'while'; isLoop: true };
|
|
296
|
+
_with: TokenType & { label: 'with'; keyword: 'with' };
|
|
297
|
+
_new: TokenType & { label: 'new'; keyword: 'new' };
|
|
298
|
+
_this: TokenType & { label: 'this'; keyword: 'this' };
|
|
299
|
+
_super: TokenType & { label: 'super'; keyword: 'super' };
|
|
300
|
+
_class: TokenType & { label: 'class'; keyword: 'class' };
|
|
301
|
+
_extends: TokenType & { label: 'extends'; keyword: 'extends' };
|
|
302
|
+
_export: TokenType & { label: 'export'; keyword: 'export' };
|
|
303
|
+
_import: TokenType & { label: 'import'; keyword: 'import' };
|
|
304
|
+
_null: TokenType & { label: 'null'; keyword: 'null' };
|
|
305
|
+
_true: TokenType & { label: 'true'; keyword: 'true' };
|
|
306
|
+
_false: TokenType & { label: 'false'; keyword: 'false' };
|
|
307
|
+
_in: TokenType & { label: 'in'; keyword: 'in'; binop: 7 };
|
|
308
|
+
_instanceof: TokenType & { label: 'instanceof'; keyword: 'instanceof'; binop: 7 };
|
|
309
|
+
_typeof: TokenType & { label: 'typeof'; keyword: 'typeof'; prefix: true };
|
|
310
|
+
_void: TokenType & { label: 'void'; keyword: 'void'; prefix: true };
|
|
311
|
+
_delete: TokenType & { label: 'delete'; keyword: 'delete'; prefix: true };
|
|
312
|
+
}
|
|
313
|
+
|
|
314
|
+
/**
|
|
315
|
+
* TypeScript-specific token types added by @sveltejs/acorn-typescript
|
|
316
|
+
*/
|
|
317
|
+
export interface AcornTypeScriptTokTypes {
|
|
318
|
+
// JSX tokens
|
|
319
|
+
jsxTagStart: TokenType & { label: 'jsxTagStart' };
|
|
320
|
+
jsxTagEnd: TokenType & { label: 'jsxTagEnd' };
|
|
321
|
+
jsxText: TokenType & { label: 'jsxText' };
|
|
322
|
+
jsxName: TokenType & { label: 'jsxName' };
|
|
323
|
+
|
|
324
|
+
// Decorator token
|
|
325
|
+
at: TokenType & { label: '@' };
|
|
326
|
+
|
|
327
|
+
// TypeScript keyword tokens
|
|
328
|
+
abstract: TokenType & { label: 'abstract' };
|
|
329
|
+
as: TokenType & { label: 'as' };
|
|
330
|
+
asserts: TokenType & { label: 'asserts' };
|
|
331
|
+
assert: TokenType & { label: 'assert' };
|
|
332
|
+
bigint: TokenType & { label: 'bigint' };
|
|
333
|
+
declare: TokenType & { label: 'declare' };
|
|
334
|
+
enum: TokenType & { label: 'enum' };
|
|
335
|
+
global: TokenType & { label: 'global' };
|
|
336
|
+
implements: TokenType & { label: 'implements' };
|
|
337
|
+
infer: TokenType & { label: 'infer' };
|
|
338
|
+
interface: TokenType & { label: 'interface' };
|
|
339
|
+
intrinsic: TokenType & { label: 'intrinsic' };
|
|
340
|
+
is: TokenType & { label: 'is' };
|
|
341
|
+
keyof: TokenType & { label: 'keyof' };
|
|
342
|
+
module: TokenType & { label: 'module' };
|
|
343
|
+
namespace: TokenType & { label: 'namespace' };
|
|
344
|
+
never: TokenType & { label: 'never' };
|
|
345
|
+
out: TokenType & { label: 'out' };
|
|
346
|
+
override: TokenType & { label: 'override' };
|
|
347
|
+
private: TokenType & { label: 'private' };
|
|
348
|
+
protected: TokenType & { label: 'protected' };
|
|
349
|
+
public: TokenType & { label: 'public' };
|
|
350
|
+
readonly: TokenType & { label: 'readonly' };
|
|
351
|
+
require: TokenType & { label: 'require' };
|
|
352
|
+
satisfies: TokenType & { label: 'satisfies' };
|
|
353
|
+
symbol: TokenType & { label: 'symbol' };
|
|
354
|
+
type: TokenType & { label: 'type' };
|
|
355
|
+
unique: TokenType & { label: 'unique' };
|
|
356
|
+
unknown: TokenType & { label: 'unknown' };
|
|
357
|
+
}
|
|
358
|
+
|
|
359
|
+
/**
|
|
360
|
+
* TypeScript-specific token contexts added by @sveltejs/acorn-typescript
|
|
361
|
+
*/
|
|
362
|
+
export interface AcornTypeScriptTokContexts {
|
|
363
|
+
/** JSX opening tag context - `<` starting a JSX tag */
|
|
364
|
+
tc_oTag: TokContext & { token: '<' };
|
|
365
|
+
/** JSX closing tag context - `</` closing a JSX tag */
|
|
366
|
+
tc_cTag: TokContext & { token: '</' };
|
|
367
|
+
/** JSX expression context - `{` inside JSX for expressions */
|
|
368
|
+
tc_expr: TokContext & { token: '{' };
|
|
369
|
+
}
|
|
370
|
+
|
|
371
|
+
/**
|
|
372
|
+
* Combined TypeScript extensions object
|
|
373
|
+
*/
|
|
374
|
+
export interface AcornTypeScriptExtensions {
|
|
375
|
+
tokTypes: AcornTypeScriptTokTypes;
|
|
376
|
+
tokContexts: AcornTypeScriptTokContexts;
|
|
377
|
+
}
|
|
378
|
+
|
|
379
|
+
interface Scope {
|
|
380
|
+
flags: number;
|
|
381
|
+
var: string[];
|
|
382
|
+
lexical: string[];
|
|
383
|
+
functions: string[];
|
|
384
|
+
}
|
|
385
|
+
|
|
386
|
+
type Exports = Record<string, boolean>;
|
|
387
|
+
|
|
388
|
+
/**
|
|
389
|
+
* Extended Parser instance with internal properties
|
|
390
|
+
*
|
|
391
|
+
* These properties are used internally by Acorn but not exposed in official types.
|
|
392
|
+
* They are accessed by Ripple's custom parser plugin for whitespace handling,
|
|
393
|
+
* JSX parsing, and other advanced features.
|
|
394
|
+
*/
|
|
395
|
+
export interface Parser {
|
|
396
|
+
// ============================================================
|
|
397
|
+
// Position and Location Tracking
|
|
398
|
+
// ============================================================
|
|
399
|
+
/** Start position of the current token (0-indexed) */
|
|
400
|
+
start: number;
|
|
401
|
+
/** End position of the current token (0-indexed) */
|
|
402
|
+
end: number;
|
|
403
|
+
/** Current parsing position in input string (0-indexed) */
|
|
404
|
+
pos: number;
|
|
405
|
+
/** Current line number (1-indexed) */
|
|
406
|
+
curLine: number;
|
|
407
|
+
/** Position where the current line starts (0-indexed) */
|
|
408
|
+
lineStart: number;
|
|
409
|
+
|
|
410
|
+
/** Start location of current token */
|
|
411
|
+
startLoc: AST.Position;
|
|
412
|
+
/** End location of current token */
|
|
413
|
+
endLoc: AST.Position;
|
|
414
|
+
/** End position of the last token */
|
|
415
|
+
lastTokEnd: number;
|
|
416
|
+
/** Start position of the last token */
|
|
417
|
+
lastTokStart: number;
|
|
418
|
+
/** End location of the last token */
|
|
419
|
+
lastTokEndLoc: AST.Position;
|
|
420
|
+
/** Start location of the last token */
|
|
421
|
+
lastTokStartLoc: AST.Position;
|
|
422
|
+
|
|
423
|
+
// ============================================================
|
|
424
|
+
// Current Token State
|
|
425
|
+
// ============================================================
|
|
426
|
+
/** Current token type */
|
|
427
|
+
type: TokenType;
|
|
428
|
+
/** Current token value (string for names, number for nums, etc.) */
|
|
429
|
+
value: string | number | RegExp | bigint | null;
|
|
430
|
+
|
|
431
|
+
// ============================================================
|
|
432
|
+
// Parser State
|
|
433
|
+
// ============================================================
|
|
434
|
+
/** The source code being parsed */
|
|
435
|
+
input: string;
|
|
436
|
+
/** Whether the current position expects an expression */
|
|
437
|
+
exprAllowed: boolean;
|
|
438
|
+
/** Whether the parser is in strict mode */
|
|
439
|
+
strict: boolean;
|
|
440
|
+
/** Whether we're inside a generator function */
|
|
441
|
+
inGenerator: boolean;
|
|
442
|
+
/** Whether we're inside an async function */
|
|
443
|
+
inAsync: boolean;
|
|
444
|
+
/** Whether we're inside a function */
|
|
445
|
+
inFunction: boolean;
|
|
446
|
+
/** Stack of label names for break/continue statements */
|
|
447
|
+
labels: Array<{ kind: string | null; name?: string; statementStart?: number }>;
|
|
448
|
+
/** Current scope flags stack */
|
|
449
|
+
scopeStack: Array<{ flags: number; var: string[]; lexical: string[]; functions: string[] }>;
|
|
450
|
+
/** Regular expression validation state */
|
|
451
|
+
regexpState: RegExpValidationState | null;
|
|
452
|
+
/** Whether we can use await keyword */
|
|
453
|
+
canAwait: boolean;
|
|
454
|
+
/** Position of await keyword (0 if not in async context) */
|
|
455
|
+
awaitPos: number;
|
|
456
|
+
/** Position of yield keyword (0 if not in generator context) */
|
|
457
|
+
yieldPos: number;
|
|
458
|
+
/** Position of await used as identifier (for error reporting) */
|
|
459
|
+
awaitIdentPos: number;
|
|
460
|
+
/** Whether current identifier contains escape sequences */
|
|
461
|
+
containsEsc: boolean;
|
|
462
|
+
/** Potential arrow function position */
|
|
463
|
+
potentialArrowAt: number;
|
|
464
|
+
/** Potential arrow in for-await position */
|
|
465
|
+
potentialArrowInForAwait: boolean;
|
|
466
|
+
/** Private name stack for class private fields validation */
|
|
467
|
+
privateNameStack: Array<{ declared: Record<string, string>; used: Array<AST.Node> }>;
|
|
468
|
+
/** Undefined exports for module validation */
|
|
469
|
+
undefinedExports: Record<string, AST.Node>;
|
|
470
|
+
|
|
471
|
+
// ============================================================
|
|
472
|
+
// Context Stack
|
|
473
|
+
// ============================================================
|
|
474
|
+
/** Token context stack for tokenizer state */
|
|
475
|
+
context: TokContext[];
|
|
476
|
+
/** Whether to preserve spaces in current context */
|
|
477
|
+
preserveSpace?: boolean;
|
|
478
|
+
|
|
479
|
+
// ============================================================
|
|
480
|
+
// Parser Configuration
|
|
481
|
+
// ============================================================
|
|
482
|
+
/** Parser options (from constructor) */
|
|
483
|
+
options: Options;
|
|
484
|
+
/** ECMAScript version being parsed */
|
|
485
|
+
ecmaVersion: number;
|
|
486
|
+
/** Keywords regex for current ecmaVersion */
|
|
487
|
+
keywords: RegExp;
|
|
488
|
+
/** Reserved words regex */
|
|
489
|
+
reservedWords: RegExp;
|
|
490
|
+
/** Whether we're parsing a module */
|
|
491
|
+
inModule: boolean;
|
|
492
|
+
|
|
493
|
+
// ============================================================
|
|
494
|
+
// Token Methods
|
|
495
|
+
// ============================================================
|
|
496
|
+
/**
|
|
497
|
+
* Finish current token with given type and optional value
|
|
498
|
+
* @see https://github.com/acornjs/acorn/blob/main/acorn/src/tokenize.js
|
|
499
|
+
*/
|
|
500
|
+
finishToken(type: TokenType, val?: string | number | RegExp | bigint): void;
|
|
501
|
+
|
|
502
|
+
readAtIdentifier(): void;
|
|
503
|
+
|
|
504
|
+
/**
|
|
505
|
+
* Read a token based on character code
|
|
506
|
+
* Called by nextToken() for each character
|
|
507
|
+
*/
|
|
508
|
+
readToken(code: number): void;
|
|
509
|
+
|
|
510
|
+
/**
|
|
511
|
+
* Read a word (identifier or keyword)
|
|
512
|
+
* @returns Token type (name or keyword)
|
|
513
|
+
*/
|
|
514
|
+
readWord(): TokenType;
|
|
515
|
+
|
|
516
|
+
/**
|
|
517
|
+
* Read word starting from current position
|
|
518
|
+
* @returns The word string
|
|
519
|
+
*/
|
|
520
|
+
readWord1(): string;
|
|
521
|
+
|
|
522
|
+
/** Read a number literal */
|
|
523
|
+
readNumber(startsWithDot: boolean): void;
|
|
524
|
+
|
|
525
|
+
/** Read a string literal */
|
|
526
|
+
readString(quote: number): void;
|
|
527
|
+
|
|
528
|
+
/** Read a template token */
|
|
529
|
+
readTmplToken(): void;
|
|
530
|
+
|
|
531
|
+
/** Read a regular expression literal */
|
|
532
|
+
readRegexp(): void;
|
|
533
|
+
|
|
534
|
+
/** Skip block comment, tracking line positions */
|
|
535
|
+
skipBlockComment(): void;
|
|
536
|
+
|
|
537
|
+
/** Skip line comment */
|
|
538
|
+
skipLineComment(startSkip: number): void;
|
|
539
|
+
|
|
540
|
+
/** Skip whitespace and comments */
|
|
541
|
+
skipSpace(): void;
|
|
542
|
+
|
|
543
|
+
/** Read and return the next token */
|
|
544
|
+
nextToken(): void;
|
|
545
|
+
|
|
546
|
+
/** Advance to next token (wrapper around nextToken) */
|
|
547
|
+
next(): void;
|
|
548
|
+
|
|
549
|
+
/**
|
|
550
|
+
* Get token from character code
|
|
551
|
+
* Main tokenizer dispatch based on first character
|
|
552
|
+
*/
|
|
553
|
+
getTokenFromCode(code: number): void;
|
|
554
|
+
|
|
555
|
+
/**
|
|
556
|
+
* Get current position as Position object
|
|
557
|
+
* @returns { line: number, column: number, index: number }
|
|
558
|
+
*/
|
|
559
|
+
curPosition(): AST.Position;
|
|
560
|
+
|
|
561
|
+
/**
|
|
562
|
+
* Finish building an operator token
|
|
563
|
+
* @param type Token type
|
|
564
|
+
* @param size Number of characters consumed
|
|
565
|
+
*/
|
|
566
|
+
finishOp(type: TokenType, size: number): TokenType;
|
|
567
|
+
|
|
568
|
+
// ============================================================
|
|
569
|
+
// Node Creation Methods
|
|
570
|
+
// ============================================================
|
|
571
|
+
/**
|
|
572
|
+
* Finish a node, setting its end position and type
|
|
573
|
+
* @template T Node type extending AST.Node
|
|
574
|
+
* @param node The node to finish
|
|
575
|
+
* @param type The node type string (e.g., "Identifier", "BinaryExpression")
|
|
576
|
+
* @returns The finished node
|
|
577
|
+
*/
|
|
578
|
+
finishNode<T extends AST.Node>(node: T, type: string): T;
|
|
579
|
+
|
|
580
|
+
/**
|
|
581
|
+
* Finish a node at a specific position
|
|
582
|
+
*/
|
|
583
|
+
finishNodeAt<T extends AST.Node>(node: T, type: string, pos: number, loc: AST.Position): T;
|
|
584
|
+
|
|
585
|
+
/**
|
|
586
|
+
* Start a new node at current position
|
|
587
|
+
*/
|
|
588
|
+
startNode(): AST.Node;
|
|
589
|
+
|
|
590
|
+
/**
|
|
591
|
+
* Start a new node at a specific position
|
|
592
|
+
* @param pos Start position
|
|
593
|
+
* @param loc Start location
|
|
594
|
+
* @returns A new node with specified start position
|
|
595
|
+
*/
|
|
596
|
+
startNodeAt(pos: number, loc: AST.Position): AST.Node;
|
|
597
|
+
|
|
598
|
+
/**
|
|
599
|
+
* Start a node at the same position as another node
|
|
600
|
+
* @param node The node to copy position from
|
|
601
|
+
* @returns A new node with copied start position
|
|
602
|
+
*/
|
|
603
|
+
startNodeAtNode(node: AST.Node): AST.Node;
|
|
604
|
+
|
|
605
|
+
/**
|
|
606
|
+
* Copy a node's position info
|
|
607
|
+
* @template T Node type
|
|
608
|
+
* @param node The node to copy
|
|
609
|
+
* @returns A shallow copy of the node
|
|
610
|
+
*/
|
|
611
|
+
copyNode<T extends AST.Node>(node: T): T;
|
|
612
|
+
|
|
613
|
+
/**
|
|
614
|
+
* Reset end location from another node
|
|
615
|
+
* @param node Node to update
|
|
616
|
+
*/
|
|
617
|
+
resetEndLocation(node: AST.Node): void;
|
|
618
|
+
|
|
619
|
+
/**
|
|
620
|
+
* Reset start location from another node
|
|
621
|
+
* @param node Node to update
|
|
622
|
+
* @param locationNode Node to copy from
|
|
623
|
+
*/
|
|
624
|
+
resetStartLocationFromNode(node: AST.Node, locationNode: AST.Node): void;
|
|
625
|
+
|
|
626
|
+
// ============================================================
|
|
627
|
+
// Error Handling
|
|
628
|
+
// ============================================================
|
|
629
|
+
/**
|
|
630
|
+
* Raise a fatal error at given position
|
|
631
|
+
* @throws SyntaxError
|
|
632
|
+
*/
|
|
633
|
+
raise(pos: number, message: string): never;
|
|
634
|
+
|
|
635
|
+
/**
|
|
636
|
+
* Raise a recoverable error (warning that doesn't stop parsing)
|
|
637
|
+
*/
|
|
638
|
+
raiseRecoverable(pos: number, message: string): void;
|
|
639
|
+
|
|
640
|
+
/**
|
|
641
|
+
* Throw unexpected token error
|
|
642
|
+
* @param pos Optional position (defaults to current)
|
|
643
|
+
*/
|
|
644
|
+
unexpected(pos?: number): never;
|
|
645
|
+
|
|
646
|
+
// ============================================================
|
|
647
|
+
// Token Consumption Methods
|
|
648
|
+
// ============================================================
|
|
649
|
+
/**
|
|
650
|
+
* Expect a specific token type, raise error if not found
|
|
651
|
+
* @param type Expected token type
|
|
652
|
+
*/
|
|
653
|
+
expect(type: TokenType): void;
|
|
654
|
+
|
|
655
|
+
/**
|
|
656
|
+
* Consume token if it matches, return true if consumed
|
|
657
|
+
* @param type Token type to eat
|
|
658
|
+
* @returns true if token was consumed
|
|
659
|
+
*/
|
|
660
|
+
eat(type: TokenType): boolean;
|
|
661
|
+
|
|
662
|
+
/**
|
|
663
|
+
* Check if current token matches type (alias for this.type === type)
|
|
664
|
+
* @param type Token type to match
|
|
665
|
+
*/
|
|
666
|
+
match(type: TokenType): boolean;
|
|
667
|
+
|
|
668
|
+
/**
|
|
669
|
+
* Peek at character at position
|
|
670
|
+
* @deprecated Use charCodeAt instead
|
|
671
|
+
*/
|
|
672
|
+
charAt(pos: number): string;
|
|
673
|
+
|
|
674
|
+
/**
|
|
675
|
+
* Get character code at position in input
|
|
676
|
+
*/
|
|
677
|
+
charCodeAt(pos: number): number;
|
|
678
|
+
|
|
679
|
+
/**
|
|
680
|
+
* Check if current token is a contextual keyword
|
|
681
|
+
* @param name Keyword to check (e.g., "async", "of")
|
|
682
|
+
*/
|
|
683
|
+
isContextual(name: string): boolean;
|
|
684
|
+
|
|
685
|
+
/**
|
|
686
|
+
* Consume if current token is a contextual keyword
|
|
687
|
+
* @param name Keyword to consume
|
|
688
|
+
* @returns true if consumed
|
|
689
|
+
*/
|
|
690
|
+
eatContextual(name: string): boolean;
|
|
691
|
+
|
|
692
|
+
/**
|
|
693
|
+
* Expect a contextual keyword, raise error if not found
|
|
694
|
+
* @param name Expected keyword
|
|
695
|
+
*/
|
|
696
|
+
expectContextual(name: string): void;
|
|
697
|
+
|
|
698
|
+
/**
|
|
699
|
+
* Check if semicolon can be inserted at current position (ASI)
|
|
700
|
+
*/
|
|
701
|
+
canInsertSemicolon(): boolean;
|
|
702
|
+
|
|
703
|
+
/**
|
|
704
|
+
* Insert a semicolon if allowed by ASI rules
|
|
705
|
+
* returns true if semicolon was inserted
|
|
706
|
+
*/
|
|
707
|
+
insertSemicolon(): boolean;
|
|
708
|
+
|
|
709
|
+
/**
|
|
710
|
+
* Consume semicolon or insert via ASI
|
|
711
|
+
*/
|
|
712
|
+
semicolon(): void;
|
|
713
|
+
|
|
714
|
+
/**
|
|
715
|
+
* Handle trailing comma in lists
|
|
716
|
+
*/
|
|
717
|
+
afterTrailingComma(type: TokenType, notNext?: boolean): boolean;
|
|
718
|
+
|
|
719
|
+
// ============================================================
|
|
720
|
+
// Scope Management
|
|
721
|
+
// ============================================================
|
|
722
|
+
/**
|
|
723
|
+
* Enter a new scope
|
|
724
|
+
* @param flags Scope flags (SCOPE_* constants)
|
|
725
|
+
*/
|
|
726
|
+
enterScope(flags: number): void;
|
|
727
|
+
|
|
728
|
+
/** Exit current scope */
|
|
729
|
+
exitScope(): void;
|
|
730
|
+
|
|
731
|
+
/**
|
|
732
|
+
* Declare a name in current scope
|
|
733
|
+
*/
|
|
734
|
+
declareName(name: string, bindingType: BindingType[keyof BindingType], pos: number): void;
|
|
735
|
+
|
|
736
|
+
/** Get current scope */
|
|
737
|
+
currentScope(): Scope;
|
|
738
|
+
|
|
739
|
+
/** Get current variable scope (for var declarations) */
|
|
740
|
+
currentVarScope(): Scope;
|
|
741
|
+
|
|
742
|
+
/** Get current "this" scope */
|
|
743
|
+
currentThisScope(): Scope;
|
|
744
|
+
|
|
745
|
+
/** Check if treating functions as var in current scope */
|
|
746
|
+
treatFunctionsAsVarInScope(scope: Scope): boolean;
|
|
747
|
+
|
|
748
|
+
// ============================================================
|
|
749
|
+
// Context Management
|
|
750
|
+
// ============================================================
|
|
751
|
+
/**
|
|
752
|
+
* Get current token context
|
|
753
|
+
* @returns Current context from stack
|
|
754
|
+
*/
|
|
755
|
+
curContext(): TokContext;
|
|
756
|
+
|
|
757
|
+
/**
|
|
758
|
+
* Update token context based on previous token
|
|
759
|
+
* @param prevType Previous token type
|
|
760
|
+
*/
|
|
761
|
+
updateContext(prevType: TokenType): void;
|
|
762
|
+
|
|
763
|
+
/**
|
|
764
|
+
* Override the current context
|
|
765
|
+
* @param context New context to push
|
|
766
|
+
*/
|
|
767
|
+
overrideContext(context: TokContext): void;
|
|
768
|
+
|
|
769
|
+
// ============================================================
|
|
770
|
+
// Lookahead
|
|
771
|
+
// ============================================================
|
|
772
|
+
/**
|
|
773
|
+
* Look ahead one token without consuming
|
|
774
|
+
* @returns Object with type and value of next token
|
|
775
|
+
*/
|
|
776
|
+
lookahead(): { type: TokenType; value: any };
|
|
777
|
+
|
|
778
|
+
/**
|
|
779
|
+
* Get next token start position
|
|
780
|
+
*/
|
|
781
|
+
nextTokenStart(): number;
|
|
782
|
+
|
|
783
|
+
/**
|
|
784
|
+
* Get next token start since given position
|
|
785
|
+
*/
|
|
786
|
+
nextTokenStartSince(pos: number): number;
|
|
787
|
+
|
|
788
|
+
/**
|
|
789
|
+
* Look ahead at character code
|
|
790
|
+
*/
|
|
791
|
+
lookaheadCharCode(): number;
|
|
792
|
+
|
|
793
|
+
// ============================================================
|
|
794
|
+
// Expression Parsing
|
|
795
|
+
// ============================================================
|
|
796
|
+
/**
|
|
797
|
+
* Parse an expression
|
|
798
|
+
*/
|
|
799
|
+
parseExpression(
|
|
800
|
+
forInit?: ForInit,
|
|
801
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
802
|
+
): AST.Expression;
|
|
803
|
+
|
|
804
|
+
/**
|
|
805
|
+
* Parse maybe-assignment expression (handles = and op=)
|
|
806
|
+
*/
|
|
807
|
+
parseMaybeAssign(
|
|
808
|
+
forInit?: ForInit,
|
|
809
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
810
|
+
afterLeftParse?: (node: AST.Node, startPos: number, startLoc: AST.Position) => AST.Node,
|
|
811
|
+
): AST.Expression;
|
|
812
|
+
|
|
813
|
+
/**
|
|
814
|
+
* Parse maybe-conditional expression (?:)
|
|
815
|
+
*/
|
|
816
|
+
parseMaybeConditional(
|
|
817
|
+
forInit?: ForInit,
|
|
818
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
819
|
+
): AST.Expression;
|
|
820
|
+
|
|
821
|
+
/**
|
|
822
|
+
* Parse expression with operators (handles precedence)
|
|
823
|
+
*/
|
|
824
|
+
parseExprOps(forInit?: ForInit, refDestructuringErrors?: DestructuringErrors): AST.Expression;
|
|
825
|
+
|
|
826
|
+
/**
|
|
827
|
+
* Parse expression with operator at given precedence
|
|
828
|
+
*/
|
|
829
|
+
parseExprOp(
|
|
830
|
+
left: AST.Expression,
|
|
831
|
+
leftStartPos: number,
|
|
832
|
+
leftStartLoc: AST.Position,
|
|
833
|
+
minPrec: number,
|
|
834
|
+
forInit?: ForInit,
|
|
835
|
+
): AST.Expression;
|
|
836
|
+
|
|
837
|
+
/**
|
|
838
|
+
* Parse maybe-unary expression (prefix operators)
|
|
839
|
+
*/
|
|
840
|
+
parseMaybeUnary(
|
|
841
|
+
refDestructuringErrors?: DestructuringErrors | null,
|
|
842
|
+
sawUnary?: boolean,
|
|
843
|
+
incDec?: boolean,
|
|
844
|
+
forInit?: ForInit,
|
|
845
|
+
): AST.Expression;
|
|
846
|
+
|
|
847
|
+
/**
|
|
848
|
+
* Parse expression subscripts (member access, calls)
|
|
849
|
+
*/
|
|
850
|
+
parseExprSubscripts(
|
|
851
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
852
|
+
forInit?: ForInit,
|
|
853
|
+
): AST.Expression;
|
|
854
|
+
|
|
855
|
+
/**
|
|
856
|
+
* Parse subscripts (., [], (), ?.)
|
|
857
|
+
*/
|
|
858
|
+
parseSubscripts(
|
|
859
|
+
base: AST.Expression,
|
|
860
|
+
startPos: number,
|
|
861
|
+
startLoc: AST.Position,
|
|
862
|
+
noCalls?: boolean,
|
|
863
|
+
maybeAsyncArrow?: boolean,
|
|
864
|
+
optionalChained?: boolean,
|
|
865
|
+
forInit?: ForInit,
|
|
866
|
+
): AST.Expression;
|
|
867
|
+
|
|
868
|
+
parseSubscript(
|
|
869
|
+
base: AST.Expression,
|
|
870
|
+
startPos: number,
|
|
871
|
+
startLoc: AST.Position,
|
|
872
|
+
noCalls?: boolean,
|
|
873
|
+
maybeAsyncArrow?: boolean,
|
|
874
|
+
optionalChained?: boolean,
|
|
875
|
+
forInit?: ForInit,
|
|
876
|
+
): AST.Expression;
|
|
877
|
+
|
|
878
|
+
/**
|
|
879
|
+
* Parse expression atom (literals, identifiers, etc.)
|
|
880
|
+
*/
|
|
881
|
+
parseExprAtom(
|
|
882
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
883
|
+
forInit?: ForInit,
|
|
884
|
+
forNew?: boolean,
|
|
885
|
+
):
|
|
886
|
+
| AST.ServerIdentifier
|
|
887
|
+
| AST.TrackedExpression
|
|
888
|
+
| AST.TrackedMapExpression
|
|
889
|
+
| AST.TrackedSetExpression
|
|
890
|
+
| AST.TrackedArrayExpression
|
|
891
|
+
| AST.TrackedObjectExpression
|
|
892
|
+
| AST.Component;
|
|
893
|
+
|
|
894
|
+
/** Default handler for parseExprAtom when no other case matches */
|
|
895
|
+
parseExprAtomDefault(): AST.Expression;
|
|
896
|
+
|
|
897
|
+
/**
|
|
898
|
+
* Parse a literal value (string, number, boolean, null, regex)
|
|
899
|
+
* @param value The literal value
|
|
900
|
+
* @returns Literal node
|
|
901
|
+
*/
|
|
902
|
+
parseLiteral(value: string | number | boolean | null | RegExp | bigint): AST.Literal;
|
|
903
|
+
|
|
904
|
+
/**
|
|
905
|
+
* Parse parenthesized expression, distinguishing arrow functions
|
|
906
|
+
*/
|
|
907
|
+
parseParenAndDistinguishExpression(canBeArrow?: boolean, forInit?: ForInit): AST.Expression;
|
|
908
|
+
|
|
909
|
+
/** Parse parenthesized expression (just the expression) */
|
|
910
|
+
parseParenExpression(): AST.Expression;
|
|
911
|
+
|
|
912
|
+
parseTrackedCollectionExpression(
|
|
913
|
+
type: 'TrackedMapExpression' | 'TrackedSetExpression',
|
|
914
|
+
): AST.TrackedMapExpression | AST.TrackedSetExpression;
|
|
915
|
+
|
|
916
|
+
parseTrackedArrayExpression(): AST.TrackedArrayExpression;
|
|
917
|
+
|
|
918
|
+
parseTrackedExpression(): AST.TrackedExpression;
|
|
919
|
+
|
|
920
|
+
parseTrackedObjectExpression(): AST.TrackedObjectExpression;
|
|
921
|
+
|
|
922
|
+
/**
|
|
923
|
+
* Parse item in parentheses (can be overridden for flow/ts)
|
|
924
|
+
*/
|
|
925
|
+
parseParenItem(item: AST.Node): AST.Node;
|
|
926
|
+
|
|
927
|
+
/**
|
|
928
|
+
* Parse arrow expression
|
|
929
|
+
|
|
930
|
+
*/
|
|
931
|
+
parseArrowExpression(
|
|
932
|
+
node: AST.Node,
|
|
933
|
+
params: AST.Node[],
|
|
934
|
+
isAsync?: boolean,
|
|
935
|
+
forInit?: ForInit,
|
|
936
|
+
): AST.ArrowFunctionExpression;
|
|
937
|
+
|
|
938
|
+
/**
|
|
939
|
+
* Check if arrow should be parsed
|
|
940
|
+
*/
|
|
941
|
+
shouldParseArrow(exprList: AST.Node[]): boolean;
|
|
942
|
+
|
|
943
|
+
/**
|
|
944
|
+
* Parse spread element (...expr)
|
|
945
|
+
*/
|
|
946
|
+
parseSpread(refDestructuringErrors?: DestructuringErrors): AST.SpreadElement;
|
|
947
|
+
|
|
948
|
+
/**
|
|
949
|
+
* Parse rest binding pattern (...pattern)
|
|
950
|
+
* @returns RestElement node
|
|
951
|
+
*/
|
|
952
|
+
parseRestBinding(): AST.RestElement;
|
|
953
|
+
|
|
954
|
+
/**
|
|
955
|
+
* Parse 'new' expression
|
|
956
|
+
* @returns NewExpression or MetaProperty (new.target)
|
|
957
|
+
*/
|
|
958
|
+
parseNew(): AST.NewExpression | AST.MetaProperty;
|
|
959
|
+
|
|
960
|
+
/**
|
|
961
|
+
* Parse dynamic import expression
|
|
962
|
+
* @param forNew Whether in new expression context
|
|
963
|
+
*/
|
|
964
|
+
parseExprImport(forNew?: boolean): AST.ImportExpression | AST.MetaProperty;
|
|
965
|
+
|
|
966
|
+
/**
|
|
967
|
+
* Parse dynamic import call
|
|
968
|
+
* @param node Import expression node
|
|
969
|
+
*/
|
|
970
|
+
parseDynamicImport(node: AST.Node): AST.ImportExpression;
|
|
971
|
+
|
|
972
|
+
/**
|
|
973
|
+
* Parse import.meta
|
|
974
|
+
* @param node MetaProperty node
|
|
975
|
+
*/
|
|
976
|
+
parseImportMeta(node: AST.Node): AST.MetaProperty;
|
|
977
|
+
|
|
978
|
+
/** Parse yield expression */
|
|
979
|
+
parseYield(forInit?: ForInit): AST.YieldExpression;
|
|
980
|
+
|
|
981
|
+
/** Parse await expression */
|
|
982
|
+
parseAwait(forInit?: ForInit): AST.AwaitExpression;
|
|
983
|
+
|
|
984
|
+
/**
|
|
985
|
+
* Parse template literal
|
|
986
|
+
* @param isTagged Whether this is a tagged template
|
|
987
|
+
*/
|
|
988
|
+
parseTemplate(isTagged?: { start: number }): AST.TemplateLiteral;
|
|
989
|
+
|
|
990
|
+
/**
|
|
991
|
+
* Parse template element
|
|
992
|
+
* @param options { isTagged: boolean }
|
|
993
|
+
*/
|
|
994
|
+
parseTemplateElement(options: { isTagged: boolean }): AST.TemplateElement;
|
|
995
|
+
|
|
996
|
+
// ============================================================
|
|
997
|
+
// Identifier Parsing
|
|
998
|
+
// ============================================================
|
|
999
|
+
/**
|
|
1000
|
+
* Parse an identifier
|
|
1001
|
+
*/
|
|
1002
|
+
parseIdent(liberal?: boolean): AST.Identifier;
|
|
1003
|
+
|
|
1004
|
+
/**
|
|
1005
|
+
* Parse identifier node (internal, doesn't consume token)
|
|
1006
|
+
* @returns Partial identifier node
|
|
1007
|
+
*/
|
|
1008
|
+
parseIdentNode(): AST.Node;
|
|
1009
|
+
|
|
1010
|
+
/**
|
|
1011
|
+
* Parse private identifier (#name)
|
|
1012
|
+
* @returns PrivateIdentifier node
|
|
1013
|
+
*/
|
|
1014
|
+
parsePrivateIdent(): AST.PrivateIdentifier;
|
|
1015
|
+
|
|
1016
|
+
/**
|
|
1017
|
+
* Check if identifier is unreserved
|
|
1018
|
+
* @param ref Node with name, start, end
|
|
1019
|
+
*/
|
|
1020
|
+
checkUnreserved(ref: { name: string; start: number; end: number }): void;
|
|
1021
|
+
|
|
1022
|
+
// ============================================================
|
|
1023
|
+
// Object/Array Parsing
|
|
1024
|
+
// ============================================================
|
|
1025
|
+
/**
|
|
1026
|
+
* Parse object expression or pattern
|
|
1027
|
+
* @param isPattern Whether parsing a pattern
|
|
1028
|
+
* @param refDestructuringErrors Error collector
|
|
1029
|
+
* @returns ObjectExpression or ObjectPattern
|
|
1030
|
+
*/
|
|
1031
|
+
parseObj(
|
|
1032
|
+
isPattern?: boolean,
|
|
1033
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
1034
|
+
): AST.ObjectExpression | AST.ObjectPattern;
|
|
1035
|
+
|
|
1036
|
+
/**
|
|
1037
|
+
* Parse property in object literal
|
|
1038
|
+
* @param isPattern Whether parsing a pattern
|
|
1039
|
+
* @param refDestructuringErrors Error collector
|
|
1040
|
+
* @returns Property node
|
|
1041
|
+
*/
|
|
1042
|
+
parseProperty(
|
|
1043
|
+
isPattern: boolean,
|
|
1044
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
1045
|
+
): AST.Property | AST.SpreadElement;
|
|
1046
|
+
|
|
1047
|
+
/**
|
|
1048
|
+
* Parse property name (identifier, string, number, computed)
|
|
1049
|
+
* @param prop Property node to update
|
|
1050
|
+
* @returns The key expression
|
|
1051
|
+
*/
|
|
1052
|
+
parsePropertyName(prop: AST.Node): AST.Expression | AST.PrivateIdentifier;
|
|
1053
|
+
|
|
1054
|
+
/**
|
|
1055
|
+
* Parse property value
|
|
1056
|
+
* @param prop Property node
|
|
1057
|
+
* @param isPattern Whether parsing pattern
|
|
1058
|
+
* @param isGenerator Whether generator method
|
|
1059
|
+
* @param isAsync Whether async method
|
|
1060
|
+
* @param startPos Start position
|
|
1061
|
+
* @param startLoc Start location
|
|
1062
|
+
* @param refDestructuringErrors Error collector
|
|
1063
|
+
* @param containsEsc Whether key contains escapes
|
|
1064
|
+
*/
|
|
1065
|
+
parsePropertyValue(
|
|
1066
|
+
prop: AST.Node,
|
|
1067
|
+
isPattern: boolean,
|
|
1068
|
+
isGenerator: boolean,
|
|
1069
|
+
isAsync: boolean,
|
|
1070
|
+
startPos: number,
|
|
1071
|
+
startLoc: AST.Position,
|
|
1072
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
1073
|
+
containsEsc?: boolean,
|
|
1074
|
+
): void;
|
|
1075
|
+
|
|
1076
|
+
/**
|
|
1077
|
+
* Get property kind from name
|
|
1078
|
+
* @param prop Property node
|
|
1079
|
+
* @returns "init", "get", or "set"
|
|
1080
|
+
*/
|
|
1081
|
+
getPropertyKind(prop: AST.Node): 'init' | 'get' | 'set';
|
|
1082
|
+
|
|
1083
|
+
/**
|
|
1084
|
+
* Parse expression list (array elements, call arguments)
|
|
1085
|
+
* @param close Closing token type
|
|
1086
|
+
* @param allowTrailingComma Whether trailing comma allowed
|
|
1087
|
+
* @param allowEmpty Whether empty slots allowed
|
|
1088
|
+
* @param refDestructuringErrors Error collector
|
|
1089
|
+
* @returns Array of expressions
|
|
1090
|
+
*/
|
|
1091
|
+
parseExprList(
|
|
1092
|
+
close: TokenType,
|
|
1093
|
+
allowTrailingComma?: boolean,
|
|
1094
|
+
allowEmpty?: boolean,
|
|
1095
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
1096
|
+
): (AST.Expression | null)[];
|
|
1097
|
+
|
|
1098
|
+
/**
|
|
1099
|
+
* Parse binding list (pattern elements)
|
|
1100
|
+
* @param close Closing token type
|
|
1101
|
+
* @param allowEmpty Whether empty slots allowed
|
|
1102
|
+
* @param allowTrailingComma Whether trailing comma allowed
|
|
1103
|
+
* @param allowModifiers Whether modifiers allowed (TS)
|
|
1104
|
+
*/
|
|
1105
|
+
parseBindingList(
|
|
1106
|
+
close: TokenType,
|
|
1107
|
+
allowEmpty?: boolean,
|
|
1108
|
+
allowTrailingComma?: boolean,
|
|
1109
|
+
allowModifiers?: boolean,
|
|
1110
|
+
): AST.Pattern[];
|
|
1111
|
+
|
|
1112
|
+
/**
|
|
1113
|
+
* Parse binding atom (identifier or pattern)
|
|
1114
|
+
* @returns Pattern node
|
|
1115
|
+
*/
|
|
1116
|
+
parseBindingAtom(): AST.Pattern;
|
|
1117
|
+
|
|
1118
|
+
// ============================================================
|
|
1119
|
+
// Statement Parsing
|
|
1120
|
+
// ============================================================
|
|
1121
|
+
/**
|
|
1122
|
+
* Parse top level program
|
|
1123
|
+
* @param node Program node to populate
|
|
1124
|
+
* @returns Completed Program node
|
|
1125
|
+
*/
|
|
1126
|
+
parseTopLevel(node: AST.Program): AST.Program;
|
|
1127
|
+
|
|
1128
|
+
parseServerBlock(): AST.ServerBlock;
|
|
1129
|
+
|
|
1130
|
+
parseElement(): AST.Element | AST.TsxCompat;
|
|
1131
|
+
|
|
1132
|
+
parseTemplateBody(
|
|
1133
|
+
body: (AST.Statement | AST.Node | ESTreeJSX.JSXText | ESTreeJSX.JSXElement['children'])[],
|
|
1134
|
+
): void;
|
|
1135
|
+
|
|
1136
|
+
parseComponent(
|
|
1137
|
+
params?:
|
|
1138
|
+
| {
|
|
1139
|
+
requireName?: boolean;
|
|
1140
|
+
isDefault?: boolean;
|
|
1141
|
+
declareName?: boolean;
|
|
1142
|
+
}
|
|
1143
|
+
| undefined,
|
|
1144
|
+
): AST.Component;
|
|
1145
|
+
|
|
1146
|
+
/**
|
|
1147
|
+
* Parse a statement
|
|
1148
|
+
* @param context Statement context ("for", "if", "label", etc.)
|
|
1149
|
+
* @param topLevel Whether at top level
|
|
1150
|
+
* @param exports Export set for module
|
|
1151
|
+
* @returns Statement node
|
|
1152
|
+
*/
|
|
1153
|
+
parseStatement(
|
|
1154
|
+
context?: string | null,
|
|
1155
|
+
topLevel?: boolean,
|
|
1156
|
+
exports?: AST.ExportSpecifier,
|
|
1157
|
+
):
|
|
1158
|
+
| AST.TextNode
|
|
1159
|
+
| ESTreeJSX.JSXEmptyExpression
|
|
1160
|
+
| ESTreeJSX.JSXExpressionContainer
|
|
1161
|
+
| AST.ServerBlock
|
|
1162
|
+
| AST.Component
|
|
1163
|
+
| AST.ExpressionStatement
|
|
1164
|
+
| ReturnType<Parser['parseElement']>
|
|
1165
|
+
| AST.Statement;
|
|
1166
|
+
|
|
1167
|
+
parseBlock(
|
|
1168
|
+
createNewLexicalScope?: boolean,
|
|
1169
|
+
node?: AST.BlockStatement,
|
|
1170
|
+
exitStrict?: boolean,
|
|
1171
|
+
): AST.BlockStatement;
|
|
1172
|
+
|
|
1173
|
+
/** Parse empty statement (;) */
|
|
1174
|
+
parseEmptyStatement(node: AST.Node): AST.EmptyStatement;
|
|
1175
|
+
|
|
1176
|
+
/** Parse expression statement */
|
|
1177
|
+
parseExpressionStatement(node: AST.Node, expr: AST.Expression): AST.ExpressionStatement;
|
|
1178
|
+
|
|
1179
|
+
/** Parse labeled statement */
|
|
1180
|
+
parseLabeledStatement(
|
|
1181
|
+
node: AST.Node,
|
|
1182
|
+
maybeName: string,
|
|
1183
|
+
expr: AST.Expression,
|
|
1184
|
+
context?: string,
|
|
1185
|
+
): AST.LabeledStatement;
|
|
1186
|
+
|
|
1187
|
+
/** Parse if statement */
|
|
1188
|
+
parseIfStatement(node: AST.Node): AST.IfStatement;
|
|
1189
|
+
|
|
1190
|
+
/** Parse switch statement */
|
|
1191
|
+
parseSwitchStatement(node: AST.Node): AST.SwitchStatement;
|
|
1192
|
+
|
|
1193
|
+
/** Parse while statement */
|
|
1194
|
+
parseWhileStatement(node: AST.Node): AST.WhileStatement;
|
|
1195
|
+
|
|
1196
|
+
/** Parse do-while statement */
|
|
1197
|
+
parseDoStatement(node: AST.Node): AST.DoWhileStatement;
|
|
1198
|
+
|
|
1199
|
+
/** Parse for statement (all variants) */
|
|
1200
|
+
parseForStatement(
|
|
1201
|
+
node: AST.ForStatement | AST.ForInStatement | AST.ForOfStatement,
|
|
1202
|
+
): AST.ForStatement | AST.ForInStatement | AST.ForOfStatement;
|
|
1203
|
+
|
|
1204
|
+
parseForAfterInitWithIndex(
|
|
1205
|
+
node: AST.ForStatement | AST.ForInStatement | AST.ForOfStatement,
|
|
1206
|
+
init: AST.VariableDeclaration,
|
|
1207
|
+
awaitAt: number,
|
|
1208
|
+
): AST.ForStatement | AST.ForInStatement | AST.ForOfStatement;
|
|
1209
|
+
|
|
1210
|
+
parseForInWithIndex(
|
|
1211
|
+
node: AST.ForInStatement | AST.ForOfStatement,
|
|
1212
|
+
init: AST.VariableDeclaration | AST.Pattern,
|
|
1213
|
+
): AST.ForInStatement | AST.ForOfStatement;
|
|
1214
|
+
|
|
1215
|
+
/**
|
|
1216
|
+
* Parse regular for loop
|
|
1217
|
+
* @param node For statement node
|
|
1218
|
+
* @param init Initializer expression
|
|
1219
|
+
*/
|
|
1220
|
+
parseFor(node: AST.Node, init: AST.Node | null): AST.ForStatement;
|
|
1221
|
+
|
|
1222
|
+
/**
|
|
1223
|
+
* Parse for-in loop
|
|
1224
|
+
* @param node For statement node
|
|
1225
|
+
* @param init Left-hand binding
|
|
1226
|
+
*/
|
|
1227
|
+
parseForIn(node: AST.Node, init: AST.Node): AST.ForInStatement;
|
|
1228
|
+
|
|
1229
|
+
/** Parse break statement */
|
|
1230
|
+
parseBreakContinueStatement(
|
|
1231
|
+
node: AST.Node,
|
|
1232
|
+
keyword: string,
|
|
1233
|
+
): AST.BreakStatement | AST.ContinueStatement;
|
|
1234
|
+
|
|
1235
|
+
/** Parse return statement */
|
|
1236
|
+
parseReturnStatement(node: AST.Node): AST.ReturnStatement;
|
|
1237
|
+
|
|
1238
|
+
/** Parse throw statement */
|
|
1239
|
+
parseThrowStatement(node: AST.Node): AST.ThrowStatement;
|
|
1240
|
+
|
|
1241
|
+
/** Parse try statement */
|
|
1242
|
+
parseTryStatement(node: AST.TryStatement): AST.TryStatement;
|
|
1243
|
+
|
|
1244
|
+
/**
|
|
1245
|
+
* Parse catch clause parameter
|
|
1246
|
+
* @returns Pattern node for catch param
|
|
1247
|
+
*/
|
|
1248
|
+
parseCatchClauseParam(): AST.Pattern;
|
|
1249
|
+
|
|
1250
|
+
/** Parse with statement */
|
|
1251
|
+
parseWithStatement(node: AST.Node): AST.WithStatement;
|
|
1252
|
+
|
|
1253
|
+
/** Parse debugger statement */
|
|
1254
|
+
parseDebuggerStatement(node: AST.Node): AST.DebuggerStatement;
|
|
1255
|
+
|
|
1256
|
+
// ============================================================
|
|
1257
|
+
// Variable Declaration Parsing
|
|
1258
|
+
// ============================================================
|
|
1259
|
+
/** Parse variable statement (var, let, const) */
|
|
1260
|
+
parseVarStatement(node: AST.Node, kind: string): AST.VariableDeclaration;
|
|
1261
|
+
|
|
1262
|
+
/**
|
|
1263
|
+
* Parse variable declarations
|
|
1264
|
+
* @param node Declaration node
|
|
1265
|
+
* @param isFor Whether in for-loop initializer
|
|
1266
|
+
* @param kind "var", "let", "const", "using", or "await using"
|
|
1267
|
+
* @returns VariableDeclaration node
|
|
1268
|
+
*/
|
|
1269
|
+
parseVar(node: AST.Node, isFor: boolean, kind: string): AST.VariableDeclaration;
|
|
1270
|
+
|
|
1271
|
+
/**
|
|
1272
|
+
* Parse variable ID (identifier or pattern)
|
|
1273
|
+
* @param decl Declarator node
|
|
1274
|
+
* @param kind Variable kind
|
|
1275
|
+
*/
|
|
1276
|
+
parseVarId(decl: AST.Node, kind: string): void;
|
|
1277
|
+
|
|
1278
|
+
/** Check if current token starts 'let' declaration */
|
|
1279
|
+
isLet(context?: string): boolean;
|
|
1280
|
+
|
|
1281
|
+
/** Check if current token starts 'using' declaration */
|
|
1282
|
+
isUsing?(isFor?: boolean): boolean;
|
|
1283
|
+
|
|
1284
|
+
/** Check if current token starts 'await using' declaration */
|
|
1285
|
+
isAwaitUsing?(isFor?: boolean): boolean;
|
|
1286
|
+
|
|
1287
|
+
// ============================================================
|
|
1288
|
+
// Function Parsing
|
|
1289
|
+
// ============================================================
|
|
1290
|
+
/**
|
|
1291
|
+
* Parse function declaration or expression
|
|
1292
|
+
*/
|
|
1293
|
+
parseFunction(
|
|
1294
|
+
node: AST.Node,
|
|
1295
|
+
statement: number,
|
|
1296
|
+
allowExpressionBody?: boolean,
|
|
1297
|
+
isAsync?: boolean,
|
|
1298
|
+
forInit?: ForInit,
|
|
1299
|
+
): AST.FunctionDeclaration | AST.FunctionExpression;
|
|
1300
|
+
|
|
1301
|
+
/** Parse function statement */
|
|
1302
|
+
parseFunctionStatement(
|
|
1303
|
+
node: AST.Node,
|
|
1304
|
+
isAsync?: boolean,
|
|
1305
|
+
declarationPosition?: boolean,
|
|
1306
|
+
): AST.FunctionDeclaration;
|
|
1307
|
+
|
|
1308
|
+
/**
|
|
1309
|
+
* Parse function parameters into node.params
|
|
1310
|
+
* @param node Function node to populate
|
|
1311
|
+
*/
|
|
1312
|
+
parseFunctionParams(node: AST.Node): void;
|
|
1313
|
+
|
|
1314
|
+
/**
|
|
1315
|
+
* Parse function body
|
|
1316
|
+
*/
|
|
1317
|
+
parseFunctionBody(
|
|
1318
|
+
node: AST.Node,
|
|
1319
|
+
isArrowFunction: boolean,
|
|
1320
|
+
isMethod: boolean,
|
|
1321
|
+
forInit?: ForInit,
|
|
1322
|
+
): void;
|
|
1323
|
+
|
|
1324
|
+
/** Initialize function node properties */
|
|
1325
|
+
initFunction(node: AST.Node): void;
|
|
1326
|
+
|
|
1327
|
+
/** Check for yield/await in default parameters */
|
|
1328
|
+
checkYieldAwaitInDefaultParams(): void;
|
|
1329
|
+
|
|
1330
|
+
/** Check if async function */
|
|
1331
|
+
isAsyncFunction(): boolean;
|
|
1332
|
+
|
|
1333
|
+
// ============================================================
|
|
1334
|
+
// Class Parsing
|
|
1335
|
+
// ============================================================
|
|
1336
|
+
/**
|
|
1337
|
+
* Parse class declaration or expression
|
|
1338
|
+
* @param node Class node
|
|
1339
|
+
* @param isStatement true, "nullableID", or false
|
|
1340
|
+
*/
|
|
1341
|
+
parseClass(
|
|
1342
|
+
node: AST.Node,
|
|
1343
|
+
isStatement: boolean | 'nullableID',
|
|
1344
|
+
): AST.ClassDeclaration | AST.ClassExpression;
|
|
1345
|
+
|
|
1346
|
+
/** Parse class ID (name) */
|
|
1347
|
+
parseClassId(node: AST.Node, isStatement: boolean | 'nullableID'): void;
|
|
1348
|
+
|
|
1349
|
+
/** Parse class superclass */
|
|
1350
|
+
parseClassSuper(node: AST.Node): void;
|
|
1351
|
+
|
|
1352
|
+
/** Enter class body scope */
|
|
1353
|
+
enterClassBody(): Record<string, string>;
|
|
1354
|
+
|
|
1355
|
+
/** Exit class body scope */
|
|
1356
|
+
exitClassBody(): void;
|
|
1357
|
+
|
|
1358
|
+
/**
|
|
1359
|
+
* Parse class element (method, field, static block)
|
|
1360
|
+
* @param constructorAllowsSuper Whether constructor can call super
|
|
1361
|
+
*/
|
|
1362
|
+
parseClassElement(
|
|
1363
|
+
constructorAllowsSuper: boolean,
|
|
1364
|
+
): AST.MethodDefinition | AST.PropertyDefinition | AST.StaticBlock | null;
|
|
1365
|
+
|
|
1366
|
+
/** Parse class element name */
|
|
1367
|
+
parseClassElementName(element: AST.Node): void;
|
|
1368
|
+
|
|
1369
|
+
/** Parse class static block */
|
|
1370
|
+
parseClassStaticBlock(node: AST.Node): AST.StaticBlock;
|
|
1371
|
+
|
|
1372
|
+
/** Parse class method */
|
|
1373
|
+
parseClassMethod(
|
|
1374
|
+
method: AST.Node,
|
|
1375
|
+
isGenerator: boolean,
|
|
1376
|
+
isAsync: boolean,
|
|
1377
|
+
allowDirectSuper: boolean,
|
|
1378
|
+
): AST.MethodDefinition;
|
|
1379
|
+
|
|
1380
|
+
/** Parse class field */
|
|
1381
|
+
parseClassField(field: AST.Node): AST.PropertyDefinition;
|
|
1382
|
+
|
|
1383
|
+
/** Check if class element name start */
|
|
1384
|
+
isClassElementNameStart(): boolean;
|
|
1385
|
+
|
|
1386
|
+
/**
|
|
1387
|
+
* Parse method definition
|
|
1388
|
+
* @param isGenerator Whether generator method
|
|
1389
|
+
* @param isAsync Whether async method
|
|
1390
|
+
* @param allowDirectSuper Whether super() allowed
|
|
1391
|
+
*/
|
|
1392
|
+
parseMethod(
|
|
1393
|
+
isGenerator: boolean,
|
|
1394
|
+
isAsync?: boolean,
|
|
1395
|
+
allowDirectSuper?: boolean,
|
|
1396
|
+
): AST.FunctionExpression;
|
|
1397
|
+
|
|
1398
|
+
// ============================================================
|
|
1399
|
+
// Module Parsing (Import/Export)
|
|
1400
|
+
// ============================================================
|
|
1401
|
+
/** Parse import declaration */
|
|
1402
|
+
parseImport(node: AST.Node): AST.ImportDeclaration;
|
|
1403
|
+
|
|
1404
|
+
/** Parse import specifiers */
|
|
1405
|
+
parseImportSpecifiers(): AST.ImportSpecifier[];
|
|
1406
|
+
|
|
1407
|
+
/** Parse single import specifier */
|
|
1408
|
+
parseImportSpecifier(): AST.ImportSpecifier;
|
|
1409
|
+
|
|
1410
|
+
/** Parse module export name (identifier or string) */
|
|
1411
|
+
parseModuleExportName(): AST.Identifier | AST.Literal;
|
|
1412
|
+
|
|
1413
|
+
/** Parse export declaration */
|
|
1414
|
+
parseExport(
|
|
1415
|
+
node: AST.Node,
|
|
1416
|
+
exports?: Exports,
|
|
1417
|
+
): AST.ExportNamedDeclaration | AST.ExportDefaultDeclaration | AST.ExportAllDeclaration;
|
|
1418
|
+
|
|
1419
|
+
/** Parse export specifiers */
|
|
1420
|
+
parseExportSpecifiers(exports?: Exports): AST.ExportSpecifier[];
|
|
1421
|
+
|
|
1422
|
+
/** Parse export default declaration */
|
|
1423
|
+
parseExportDefaultDeclaration(): AST.Declaration | AST.Expression | AST.Component;
|
|
1424
|
+
|
|
1425
|
+
/** Check if export statement should be parsed */
|
|
1426
|
+
shouldParseExportStatement(): boolean;
|
|
1427
|
+
|
|
1428
|
+
/** Parse export declaration body */
|
|
1429
|
+
parseExportDeclaration(node: AST.Node): AST.Declaration;
|
|
1430
|
+
|
|
1431
|
+
// ============================================================
|
|
1432
|
+
// LValue and Pattern Checking
|
|
1433
|
+
// ============================================================
|
|
1434
|
+
/**
|
|
1435
|
+
* Convert expression to assignable pattern
|
|
1436
|
+
* @param node Expression to convert
|
|
1437
|
+
* @param isBinding Whether binding pattern
|
|
1438
|
+
* @param refDestructuringErrors Error collector
|
|
1439
|
+
*/
|
|
1440
|
+
toAssignable(
|
|
1441
|
+
node: AST.Node,
|
|
1442
|
+
isBinding?: boolean,
|
|
1443
|
+
refDestructuringErrors?: DestructuringErrors,
|
|
1444
|
+
): AST.Pattern;
|
|
1445
|
+
|
|
1446
|
+
/**
|
|
1447
|
+
* Convert expression list to assignable list
|
|
1448
|
+
* @param exprList Expression list
|
|
1449
|
+
* @param isBinding Whether binding patterns
|
|
1450
|
+
*/
|
|
1451
|
+
toAssignableList(exprList: AST.Node[], isBinding: boolean): AST.Pattern[];
|
|
1452
|
+
|
|
1453
|
+
/**
|
|
1454
|
+
* Parse maybe-default pattern (pattern = defaultValue)
|
|
1455
|
+
* @param startPos Start position
|
|
1456
|
+
* @param startLoc Start location
|
|
1457
|
+
* @param left Left-hand pattern
|
|
1458
|
+
*/
|
|
1459
|
+
parseMaybeDefault(startPos: number, startLoc: AST.Position, left?: AST.Node): AST.Pattern;
|
|
1460
|
+
|
|
1461
|
+
/**
|
|
1462
|
+
* Check left-value pattern (for destructuring)
|
|
1463
|
+
*/
|
|
1464
|
+
checkLValPattern(
|
|
1465
|
+
node: AST.Node,
|
|
1466
|
+
bindingType?: BindingType[keyof BindingType],
|
|
1467
|
+
checkClashes?: Record<string, boolean>,
|
|
1468
|
+
): void;
|
|
1469
|
+
|
|
1470
|
+
/**
|
|
1471
|
+
* Check left-value simple (identifier or member expression)
|
|
1472
|
+
*/
|
|
1473
|
+
checkLValSimple(
|
|
1474
|
+
expr: AST.Node,
|
|
1475
|
+
bindingType?: BindingType[keyof BindingType],
|
|
1476
|
+
checkClashes?: Record<string, boolean>,
|
|
1477
|
+
): void;
|
|
1478
|
+
|
|
1479
|
+
/**
|
|
1480
|
+
* Check left-value inner pattern
|
|
1481
|
+
* @param node Pattern node
|
|
1482
|
+
* @param bindingType Binding type constant
|
|
1483
|
+
* @param checkClashes Clash detection object
|
|
1484
|
+
*/
|
|
1485
|
+
checkLValInnerPattern(
|
|
1486
|
+
node: AST.Node,
|
|
1487
|
+
bindingType?: BindingType[keyof BindingType],
|
|
1488
|
+
checkClashes?: Record<string, boolean>,
|
|
1489
|
+
): void;
|
|
1490
|
+
|
|
1491
|
+
/**
|
|
1492
|
+
* Check expression errors
|
|
1493
|
+
* @param refDestructuringErrors Error collector
|
|
1494
|
+
* @param andThrow Whether to throw on error
|
|
1495
|
+
* @returns Whether there were errors
|
|
1496
|
+
*/
|
|
1497
|
+
checkExpressionErrors(
|
|
1498
|
+
refDestructuringErrors: DestructuringErrors | null,
|
|
1499
|
+
andThrow?: boolean,
|
|
1500
|
+
): boolean;
|
|
1501
|
+
|
|
1502
|
+
/**
|
|
1503
|
+
* Check if expression is simple assign target
|
|
1504
|
+
* @param expr Expression to check
|
|
1505
|
+
*/
|
|
1506
|
+
isSimpleAssignTarget(expr: AST.Node): boolean;
|
|
1507
|
+
|
|
1508
|
+
// ============================================================
|
|
1509
|
+
// JSX Methods (from @sveltejs/acorn-typescript)
|
|
1510
|
+
// ============================================================
|
|
1511
|
+
/**
|
|
1512
|
+
* Read JSX contents token
|
|
1513
|
+
*/
|
|
1514
|
+
jsx_readToken(): void;
|
|
1515
|
+
|
|
1516
|
+
/**
|
|
1517
|
+
* Read JSX word (element/attribute name)
|
|
1518
|
+
*/
|
|
1519
|
+
jsx_readWord(): void;
|
|
1520
|
+
|
|
1521
|
+
/**
|
|
1522
|
+
* Read JSX string
|
|
1523
|
+
* @param quote Quote character code
|
|
1524
|
+
*/
|
|
1525
|
+
jsx_readString(quote: number): void;
|
|
1526
|
+
|
|
1527
|
+
/**
|
|
1528
|
+
* Read JSX entity (e.g., & <)
|
|
1529
|
+
* @returns Decoded entity string
|
|
1530
|
+
*/
|
|
1531
|
+
jsx_readEntity(): string;
|
|
1532
|
+
|
|
1533
|
+
/**
|
|
1534
|
+
* Read JSX new line (handles CRLF normalization)
|
|
1535
|
+
* @param normalizeCRLF Whether to normalize CRLF to LF
|
|
1536
|
+
* @returns Newline string
|
|
1537
|
+
*/
|
|
1538
|
+
jsx_readNewLine(normalizeCRLF?: boolean): string;
|
|
1539
|
+
|
|
1540
|
+
/**
|
|
1541
|
+
* Parse JSX identifier
|
|
1542
|
+
* @returns JSXIdentifier node
|
|
1543
|
+
*/
|
|
1544
|
+
jsx_parseIdentifier(): ESTreeJSX.JSXIdentifier;
|
|
1545
|
+
|
|
1546
|
+
/**
|
|
1547
|
+
* Parse JSX namespaced name (ns:name)
|
|
1548
|
+
*/
|
|
1549
|
+
jsx_parseNamespacedName():
|
|
1550
|
+
| ESTreeJSX.JSXNamespacedName
|
|
1551
|
+
| ReturnType<Parser['jsx_parseIdentifier']>;
|
|
1552
|
+
|
|
1553
|
+
/**
|
|
1554
|
+
* Parse JSX element name (identifier, member, namespaced)
|
|
1555
|
+
*/
|
|
1556
|
+
jsx_parseElementName():
|
|
1557
|
+
| ESTreeJSX.JSXMemberExpression
|
|
1558
|
+
| ReturnType<Parser['jsx_parseNamespacedName']>
|
|
1559
|
+
| '';
|
|
1560
|
+
|
|
1561
|
+
/**
|
|
1562
|
+
* Parse JSX attribute value
|
|
1563
|
+
* @returns Attribute value (expression, string, or element)
|
|
1564
|
+
*/
|
|
1565
|
+
jsx_parseAttributeValue():
|
|
1566
|
+
| ESTreeJSX.JSXExpressionContainer
|
|
1567
|
+
| ReturnType<Parser['parseExprAtom']>;
|
|
1568
|
+
|
|
1569
|
+
/**
|
|
1570
|
+
* Parse JSX empty expression (for {})
|
|
1571
|
+
*/
|
|
1572
|
+
jsx_parseEmptyExpression(): ESTreeJSX.JSXEmptyExpression;
|
|
1573
|
+
|
|
1574
|
+
jsx_parseTupleContainer(): ESTreeJSX.JSXExpressionContainer;
|
|
1575
|
+
|
|
1576
|
+
/**
|
|
1577
|
+
* Parse JSX expression container ({...})
|
|
1578
|
+
* @returns JSXExpressionContainer node
|
|
1579
|
+
*/
|
|
1580
|
+
jsx_parseExpressionContainer(): AST.Node;
|
|
1581
|
+
|
|
1582
|
+
/**
|
|
1583
|
+
* Parse JSX attribute (name="value" or {spread})
|
|
1584
|
+
* @returns JSXAttribute or JSXSpreadAttribute
|
|
1585
|
+
*/
|
|
1586
|
+
jsx_parseAttribute(): AST.RippleAttribute | ESTreeJSX.JSXAttribute;
|
|
1587
|
+
|
|
1588
|
+
/**
|
|
1589
|
+
* Parse JSX opening element at position
|
|
1590
|
+
* @param startPos Start position
|
|
1591
|
+
* @param startLoc Start location
|
|
1592
|
+
* @returns JSXOpeningElement or JSXOpeningFragment
|
|
1593
|
+
*/
|
|
1594
|
+
jsx_parseOpeningElementAt(
|
|
1595
|
+
startPos?: number,
|
|
1596
|
+
startLoc?: AST.Position,
|
|
1597
|
+
): ESTreeJSX.JSXOpeningElement;
|
|
1598
|
+
// it could also be ESTreeJSX.JSXOpeningFragment
|
|
1599
|
+
// but not in our case since we don't use fragments
|
|
1600
|
+
|
|
1601
|
+
/**
|
|
1602
|
+
* Parse JSX closing element at position
|
|
1603
|
+
* @param startPos Start position
|
|
1604
|
+
* @param startLoc Start location
|
|
1605
|
+
* @returns JSXClosingElement or JSXClosingFragment
|
|
1606
|
+
*/
|
|
1607
|
+
jsx_parseClosingElementAt(startPos: number, startLoc: AST.Position): AST.Node;
|
|
1608
|
+
|
|
1609
|
+
/**
|
|
1610
|
+
* Parse JSX element at position
|
|
1611
|
+
* @param startPos Start position
|
|
1612
|
+
* @param startLoc Start location
|
|
1613
|
+
* @returns JSXElement or JSXFragment
|
|
1614
|
+
*/
|
|
1615
|
+
jsx_parseElementAt(startPos: number, startLoc: AST.Position): AST.Node;
|
|
1616
|
+
|
|
1617
|
+
/**
|
|
1618
|
+
* Parse JSX text node
|
|
1619
|
+
* @returns JSXText node
|
|
1620
|
+
*/
|
|
1621
|
+
jsx_parseText(): AST.Node;
|
|
1622
|
+
|
|
1623
|
+
/**
|
|
1624
|
+
* Parse complete JSX element
|
|
1625
|
+
* @returns JSXElement or JSXFragment
|
|
1626
|
+
*/
|
|
1627
|
+
jsx_parseElement(): AST.Node;
|
|
1628
|
+
|
|
1629
|
+
// ============================================================
|
|
1630
|
+
// Try-Parse for Recovery
|
|
1631
|
+
// ============================================================
|
|
1632
|
+
/**
|
|
1633
|
+
* Try to parse, returning result with error info if failed
|
|
1634
|
+
* @param fn Parsing function to try
|
|
1635
|
+
* @returns Result with node, error, thrown, aborted, failState
|
|
1636
|
+
*/
|
|
1637
|
+
tryParse<T>(fn: () => T): {
|
|
1638
|
+
node: T | null;
|
|
1639
|
+
error: Error | null;
|
|
1640
|
+
thrown: boolean;
|
|
1641
|
+
aborted: boolean;
|
|
1642
|
+
failState: any;
|
|
1643
|
+
};
|
|
1644
|
+
parse(input: string, options: Options): AST.Program;
|
|
1645
|
+
|
|
1646
|
+
getElementName(node?: AST.Node): string | null;
|
|
1647
|
+
}
|
|
1648
|
+
|
|
1649
|
+
/**
|
|
1650
|
+
* The constructor/class type for the extended Ripple parser.
|
|
1651
|
+
* This represents the static side of the parser class after extending with plugins.
|
|
1652
|
+
*/
|
|
1653
|
+
export interface ParserConstructor {
|
|
1654
|
+
new (options: Options, input: string): Parser;
|
|
1655
|
+
/** Built-in token types */
|
|
1656
|
+
tokTypes: TokTypes;
|
|
1657
|
+
/** Built-in token contexts */
|
|
1658
|
+
tokContexts: TokContexts;
|
|
1659
|
+
/** TypeScript extensions when using acorn-typescript */
|
|
1660
|
+
acornTypeScript: AcornTypeScriptExtensions;
|
|
1661
|
+
/** Static parse method that returns Ripple's extended Program type */
|
|
1662
|
+
parse(input: string, options: Options): AST.Program;
|
|
1663
|
+
/** Static parseExpressionAt method */
|
|
1664
|
+
parseExpressionAt(input: string, pos: number, options: Options): AST.Expression;
|
|
1665
|
+
/** Extend with plugins */
|
|
1666
|
+
extend(...plugins: ((BaseParser: ParserConstructor) => ParserConstructor)[]): ParserConstructor;
|
|
1667
|
+
}
|
|
1668
|
+
}
|