oxc_ast/ast/
js.rs

1//! JavaScript AST node definitions
2//!
3//! This module contains the core AST node definitions for JavaScript syntax including:
4//! - Program structure and statements
5//! - Expressions and literals
6//! - Functions and classes
7//! - Patterns and identifiers
8//! - Module declarations (import/export)
9//! - JSX syntax support
10//!
11//! The AST design follows ECMAScript specifications while providing
12//! clear distinctions between different identifier types for better type safety.
13#![expect(
14    missing_docs, // TODO: document individual struct fields
15    clippy::enum_variant_names,
16    clippy::struct_field_names,
17)]
18
19// NB: `#[span]`, `#[scope(...)]`,`#[visit(...)]` and `#[generate_derive(...)]` do NOT do anything to the code.
20// They are purely markers for codegen used in `tasks/ast_tools` and `crates/oxc_traverse/scripts`. See docs in those crates.
21// Read [`macro@oxc_ast_macros::ast`] for more information.
22
23use std::cell::Cell;
24
25use oxc_allocator::{Box, CloneIn, Dummy, GetAddress, TakeIn, Vec};
26use oxc_ast_macros::ast;
27use oxc_estree::ESTree;
28use oxc_span::{Atom, ContentEq, GetSpan, GetSpanMut, SourceType, Span};
29use oxc_syntax::{
30    operator::{
31        AssignmentOperator, BinaryOperator, LogicalOperator, UnaryOperator, UpdateOperator,
32    },
33    reference::ReferenceId,
34    scope::ScopeId,
35    symbol::SymbolId,
36};
37
38use super::{macros::inherit_variants, *};
39
40/// Represents the root of a JavaScript abstract syntax tree (AST), containing metadata about the source,
41/// directives, top-level statements, and scope information.
42#[ast(visit)]
43#[scope(
44    flags = ScopeFlags::Top,
45    strict_if = self.source_type.is_strict() || self.has_use_strict_directive(),
46)]
47#[derive(Debug)]
48#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
49#[estree(field_order(body, source_type, hashbang, span), via = ProgramConverter)]
50pub struct Program<'a> {
51    pub span: Span,
52    pub source_type: SourceType,
53    #[content_eq(skip)]
54    #[estree(skip)]
55    pub source_text: &'a str,
56    /// Sorted comments
57    #[content_eq(skip)]
58    #[estree(skip)]
59    pub comments: Vec<'a, Comment>,
60    pub hashbang: Option<Hashbang<'a>>,
61    #[estree(prepend_to = body)]
62    pub directives: Vec<'a, Directive<'a>>,
63    pub body: Vec<'a, Statement<'a>>,
64    pub scope_id: Cell<Option<ScopeId>>,
65}
66
67inherit_variants! {
68/// Represents a type for AST nodes corresponding to JavaScript's expressions.
69///
70/// Inherits variants from [`MemberExpression`]. See [`ast` module docs] for explanation of inheritance.
71///
72/// [`ast` module docs]: `super`
73#[ast(visit)]
74#[derive(Debug)]
75#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
76pub enum Expression<'a> {
77    /// See [`BooleanLiteral`] for AST node details.
78    BooleanLiteral(Box<'a, BooleanLiteral>) = 0,
79    /// See [`NullLiteral`] for AST node details.
80    NullLiteral(Box<'a, NullLiteral>) = 1,
81    /// See [`NumericLiteral`] for AST node details.
82    NumericLiteral(Box<'a, NumericLiteral<'a>>) = 2,
83    /// See [`BigIntLiteral`] for AST node details.
84    BigIntLiteral(Box<'a, BigIntLiteral<'a>>) = 3,
85    /// See [`RegExpLiteral`] for AST node details.
86    RegExpLiteral(Box<'a, RegExpLiteral<'a>>) = 4,
87    /// See [`StringLiteral`] for AST node details.
88    StringLiteral(Box<'a, StringLiteral<'a>>) = 5,
89    /// See [`TemplateLiteral`] for AST node details.
90    TemplateLiteral(Box<'a, TemplateLiteral<'a>>) = 6,
91
92    /// See [`IdentifierReference`] for AST node details.
93    Identifier(Box<'a, IdentifierReference<'a>>) = 7,
94
95    /// See [`MetaProperty`] for AST node details.
96    MetaProperty(Box<'a, MetaProperty<'a>>) = 8,
97    /// See [`Super`] for AST node details.
98    Super(Box<'a, Super>) = 9,
99
100    /// See [`ArrayExpression`] for AST node details.
101    ArrayExpression(Box<'a, ArrayExpression<'a>>) = 10,
102    /// See [`ArrowFunctionExpression`] for AST node details.
103    ArrowFunctionExpression(Box<'a, ArrowFunctionExpression<'a>>) = 11,
104    /// See [`AssignmentExpression`] for AST node details.
105    AssignmentExpression(Box<'a, AssignmentExpression<'a>>) = 12,
106    /// See [`AwaitExpression`] for AST node details.
107    AwaitExpression(Box<'a, AwaitExpression<'a>>) = 13,
108    /// See [`BinaryExpression`] for AST node details.
109    BinaryExpression(Box<'a, BinaryExpression<'a>>) = 14,
110    /// See [`CallExpression`] for AST node details.
111    CallExpression(Box<'a, CallExpression<'a>>) = 15,
112    /// See [`ChainExpression`] for AST node details.
113    ChainExpression(Box<'a, ChainExpression<'a>>) = 16,
114    /// See [`Class`] for AST node details.
115    ClassExpression(Box<'a, Class<'a>>) = 17,
116    /// See [`ConditionalExpression`] for AST node details.
117    ConditionalExpression(Box<'a, ConditionalExpression<'a>>) = 18,
118    /// See [`Function`] for AST node details.
119    #[visit(args(flags = ScopeFlags::Function))]
120    FunctionExpression(Box<'a, Function<'a>>) = 19,
121    /// See [`ImportExpression`] for AST node details.
122    ImportExpression(Box<'a, ImportExpression<'a>>) = 20,
123    /// See [`LogicalExpression`] for AST node details.
124    LogicalExpression(Box<'a, LogicalExpression<'a>>) = 21,
125    /// See [`NewExpression`] for AST node details.
126    NewExpression(Box<'a, NewExpression<'a>>) = 22,
127    /// See [`ObjectExpression`] for AST node details.
128    ObjectExpression(Box<'a, ObjectExpression<'a>>) = 23,
129    /// See [`ParenthesizedExpression`] for AST node details.
130    ParenthesizedExpression(Box<'a, ParenthesizedExpression<'a>>) = 24,
131    /// See [`SequenceExpression`] for AST node details.
132    SequenceExpression(Box<'a, SequenceExpression<'a>>) = 25,
133    /// See [`TaggedTemplateExpression`] for AST node details.
134    TaggedTemplateExpression(Box<'a, TaggedTemplateExpression<'a>>) = 26,
135    /// See [`ThisExpression`] for AST node details.
136    ThisExpression(Box<'a, ThisExpression>) = 27,
137    /// See [`UnaryExpression`] for AST node details.
138    UnaryExpression(Box<'a, UnaryExpression<'a>>) = 28,
139    /// See [`UpdateExpression`] for AST node details.
140    UpdateExpression(Box<'a, UpdateExpression<'a>>) = 29,
141    /// See [`YieldExpression`] for AST node details.
142    YieldExpression(Box<'a, YieldExpression<'a>>) = 30,
143    /// See [`PrivateInExpression`] for AST node details.
144    PrivateInExpression(Box<'a, PrivateInExpression<'a>>) = 31,
145
146    /// See [`JSXElement`] for AST node details.
147    JSXElement(Box<'a, JSXElement<'a>>) = 32,
148    /// See [`JSXFragment`] for AST node details.
149    JSXFragment(Box<'a, JSXFragment<'a>>) = 33,
150
151    /// See [`TSAsExpression`] for AST node details.
152    TSAsExpression(Box<'a, TSAsExpression<'a>>) = 34,
153    /// See [`TSSatisfiesExpression`] for AST node details.
154    TSSatisfiesExpression(Box<'a, TSSatisfiesExpression<'a>>) = 35,
155    /// See [`TSTypeAssertion`] for AST node details.
156    TSTypeAssertion(Box<'a, TSTypeAssertion<'a>>) = 36,
157    /// See [`TSNonNullExpression`] for AST node details.
158    TSNonNullExpression(Box<'a, TSNonNullExpression<'a>>) = 37,
159    /// See [`TSInstantiationExpression`] for AST node details.
160    TSInstantiationExpression(Box<'a, TSInstantiationExpression<'a>>) = 38,
161    /// See [`V8IntrinsicExpression`] for AST node details.
162    V8IntrinsicExpression(Box<'a, V8IntrinsicExpression<'a>>) = 39,
163
164    // `MemberExpression` variants added here by `inherit_variants!` macro
165    @inherit MemberExpression
166}
167}
168
169/// Macro for matching `Expression`'s variants.
170/// Includes `MemberExpression`'s variants.
171#[macro_export]
172macro_rules! match_expression {
173    ($ty:ident) => {
174        $ty::BooleanLiteral(_)
175            | $ty::NullLiteral(_)
176            | $ty::NumericLiteral(_)
177            | $ty::BigIntLiteral(_)
178            | $ty::RegExpLiteral(_)
179            | $ty::StringLiteral(_)
180            | $ty::TemplateLiteral(_)
181            | $ty::Identifier(_)
182            | $ty::MetaProperty(_)
183            | $ty::Super(_)
184            | $ty::ArrayExpression(_)
185            | $ty::ArrowFunctionExpression(_)
186            | $ty::AssignmentExpression(_)
187            | $ty::AwaitExpression(_)
188            | $ty::BinaryExpression(_)
189            | $ty::CallExpression(_)
190            | $ty::ChainExpression(_)
191            | $ty::ClassExpression(_)
192            | $ty::ConditionalExpression(_)
193            | $ty::FunctionExpression(_)
194            | $ty::ImportExpression(_)
195            | $ty::LogicalExpression(_)
196            | $ty::NewExpression(_)
197            | $ty::ObjectExpression(_)
198            | $ty::ParenthesizedExpression(_)
199            | $ty::SequenceExpression(_)
200            | $ty::TaggedTemplateExpression(_)
201            | $ty::ThisExpression(_)
202            | $ty::UnaryExpression(_)
203            | $ty::UpdateExpression(_)
204            | $ty::YieldExpression(_)
205            | $ty::PrivateInExpression(_)
206            | $ty::JSXElement(_)
207            | $ty::JSXFragment(_)
208            | $ty::TSAsExpression(_)
209            | $ty::TSSatisfiesExpression(_)
210            | $ty::TSTypeAssertion(_)
211            | $ty::TSNonNullExpression(_)
212            | $ty::TSInstantiationExpression(_)
213            | $ty::ComputedMemberExpression(_)
214            | $ty::StaticMemberExpression(_)
215            | $ty::PrivateFieldExpression(_)
216            | $ty::V8IntrinsicExpression(_)
217    };
218}
219pub use match_expression;
220
221/// `foo` in `let foo = 1;`
222///
223/// Fundamental syntactic structure used for naming variables, functions, and properties.
224/// It must start with a Unicode letter (including $ and _) and can be followed by Unicode letters,
225/// digits, `$`, or `_`.
226#[ast(visit)]
227#[derive(Debug, Clone)]
228#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
229#[estree(
230    rename = "Identifier",
231    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
232    field_order(decorators, name, optional, typeAnnotation, span),
233)]
234pub struct IdentifierName<'a> {
235    pub span: Span,
236    #[estree(json_safe)]
237    pub name: Atom<'a>,
238}
239
240/// `x` inside `func` in `const x = 0; function func() { console.log(x); }`
241///
242/// Represents an identifier reference, which is a reference to a variable, function, class, or object.
243///
244/// See: [13.1 Identifiers](https://tc39.es/ecma262/#sec-identifiers)
245#[ast(visit)]
246#[derive(Debug, Clone)]
247#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
248#[estree(
249    rename = "Identifier",
250    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
251    field_order(decorators, name, optional, typeAnnotation, span),
252)]
253pub struct IdentifierReference<'a> {
254    pub span: Span,
255    /// The name of the identifier being referenced.
256    #[estree(json_safe)]
257    pub name: Atom<'a>,
258    /// Reference ID
259    ///
260    /// Identifies what identifier this refers to, and how it is used. This is
261    /// set in the bind step of semantic analysis, and will always be [`None`]
262    /// immediately after parsing.
263    pub reference_id: Cell<Option<ReferenceId>>,
264}
265
266/// `x` in `const x = 0;`
267///
268/// Represents a binding identifier, which is an identifier that is used to declare a variable,
269/// function, class, or object.
270///
271/// See: [13.1 Identifiers](https://tc39.es/ecma262/#sec-identifiers)
272///
273/// Also see other examples in docs for [`BindingPatternKind`].
274#[ast(visit)]
275#[derive(Debug, Clone)]
276#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
277#[estree(
278    rename = "Identifier",
279    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
280    field_order(decorators, name, optional, typeAnnotation, span),
281)]
282pub struct BindingIdentifier<'a> {
283    pub span: Span,
284    /// The identifier name being bound.
285    #[estree(json_safe)]
286    pub name: Atom<'a>,
287    /// Unique identifier for this binding.
288    ///
289    /// This gets initialized during [`semantic analysis`] in the bind step. If
290    /// you choose to skip semantic analysis, this will always be [`None`].
291    ///
292    /// [`semantic analysis`]: <https://docs.rs/oxc_semantic/latest/oxc_semantic/struct.SemanticBuilder.html>
293    pub symbol_id: Cell<Option<SymbolId>>,
294}
295
296/// `loop` in `loop: while (true) { break loop; }`
297///
298/// Represents a label identifier, which is an identifier that is used to label a statement.
299///
300/// See: [13.1 Identifiers](https://tc39.es/ecma262/#sec-identifiers)
301#[ast(visit)]
302#[derive(Debug, Clone)]
303#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
304#[estree(
305    rename = "Identifier",
306    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
307    field_order(decorators, name, optional, typeAnnotation, span),
308)]
309pub struct LabelIdentifier<'a> {
310    pub span: Span,
311    #[estree(json_safe)]
312    pub name: Atom<'a>,
313}
314
315/// `this` in `return this.prop;`
316///
317/// Represents a `this` expression, which is a reference to the current object.
318#[ast(visit)]
319#[derive(Debug)]
320#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
321pub struct ThisExpression {
322    pub span: Span,
323}
324
325/// `[1, 2, ...[3, 4], null]` in `const array = [1, 2, ...[3, 4], null];`
326///
327/// Represents an array literal, which can include elements, spread elements, or null values.
328#[ast(visit)]
329#[derive(Debug)]
330#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
331pub struct ArrayExpression<'a> {
332    pub span: Span,
333    pub elements: Vec<'a, ArrayExpressionElement<'a>>,
334}
335
336inherit_variants! {
337/// Represents an element in an array literal.
338///
339/// Inherits variants from [`Expression`]. See [`ast` module docs] for explanation of inheritance.
340///
341/// [`ast` module docs]: `super`
342#[ast(visit)]
343#[derive(Debug)]
344#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
345pub enum ArrayExpressionElement<'a> {
346    /// `...[3, 4]` in `const array = [1, 2, ...[3, 4], null];`
347    SpreadElement(Box<'a, SpreadElement<'a>>) = 64,
348    /// `<empty>` in `const array = [1, , 2];`
349    ///
350    /// Array hole for sparse arrays.
351    /// <https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Trailing_commas#arrays>
352    Elision(Elision) = 65,
353    // `Expression` variants added here by `inherit_variants!` macro
354    @inherit Expression
355}
356}
357
358/// empty slot in `const array = [1, , 2];`
359///
360/// Array Expression Elision Element
361#[ast(visit)]
362#[derive(Debug, Clone)]
363#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
364#[estree(via = Null)]
365pub struct Elision {
366    pub span: Span,
367}
368
369/// `{ a: 1 }` in `const obj = { a: 1 };`
370///
371/// Represents an object literal, which can include properties, spread properties,
372/// or computed properties.
373#[ast(visit)]
374#[derive(Debug)]
375#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
376pub struct ObjectExpression<'a> {
377    pub span: Span,
378    /// Properties declared in the object
379    pub properties: Vec<'a, ObjectPropertyKind<'a>>,
380}
381
382/// Represents a property in an object literal.
383#[ast(visit)]
384#[derive(Debug)]
385#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
386pub enum ObjectPropertyKind<'a> {
387    /// `a: 1` in `const obj = { a: 1 };`
388    ObjectProperty(Box<'a, ObjectProperty<'a>>) = 0,
389    /// `...{ a: 1 }` in `const obj = { ...{ a: 1 } };`
390    SpreadProperty(Box<'a, SpreadElement<'a>>) = 1,
391}
392
393/// `a: 1` in `const obj = { a: 1 };`
394///
395/// Represents a property in an object literal.
396#[ast(visit)]
397#[derive(Debug)]
398#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
399#[estree(rename = "Property", add_fields(optional = TsFalse))]
400pub struct ObjectProperty<'a> {
401    pub span: Span,
402    pub kind: PropertyKind,
403    pub key: PropertyKey<'a>,
404    pub value: Expression<'a>,
405    pub method: bool,
406    pub shorthand: bool,
407    pub computed: bool,
408}
409
410inherit_variants! {
411/// Property Key
412///
413/// Inherits variants from [`Expression`]. See [`ast` module docs] for explanation of inheritance.
414///
415/// [`ast` module docs]: `super`
416#[ast(visit)]
417#[derive(Debug)]
418#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
419pub enum PropertyKey<'a> {
420    /// `a` in `const obj = { a: 1 }; obj.a;`
421    StaticIdentifier(Box<'a, IdentifierName<'a>>) = 64,
422    /// `#a` in `class C { #a = 1; }; const c = new C(); c.#a;`
423    PrivateIdentifier(Box<'a, PrivateIdentifier<'a>>) = 65,
424    // `Expression` variants added here by `inherit_variants!` macro
425    @inherit Expression
426}
427}
428
429/// Represents the kind of property in an object literal or class.
430#[ast]
431#[derive(Debug, Clone, Copy, PartialEq, Eq)]
432#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
433pub enum PropertyKind {
434    /// `a: 1` in `const obj = { a: 1 };`
435    Init = 0,
436    /// `get a() { return 1; }` in `const obj = { get a() { return 1; } };`
437    Get = 1,
438    /// `set a(value) { this._a = value; }` in `const obj = { set a(value) { this._a = value; } };`
439    Set = 2,
440}
441
442/// `` `Hello, ${name}` `` in `` const foo = `Hello, ${name}` ``
443///
444/// Represents a template literal, which can include quasi elements and expression elements.
445#[ast(visit)]
446#[derive(Debug)]
447#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
448pub struct TemplateLiteral<'a> {
449    pub span: Span,
450    pub quasis: Vec<'a, TemplateElement<'a>>,
451    pub expressions: Vec<'a, Expression<'a>>,
452}
453
454/// `` tag`Hello, ${name}` `` in `` const foo = tag`Hello, ${name}`; ``.
455///
456/// Or with TS type arguments:
457/// ```ts
458/// const foo = tag<T>`Hello, ${name}`;
459/// ```
460#[ast(visit)]
461#[derive(Debug)]
462#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
463pub struct TaggedTemplateExpression<'a> {
464    pub span: Span,
465    pub tag: Expression<'a>,
466    #[ts]
467    pub type_arguments: Option<Box<'a, TSTypeParameterInstantiation<'a>>>,
468    pub quasi: TemplateLiteral<'a>,
469}
470
471/// `Hello, ` in `` `Hello, ${name}` ``
472///
473/// Represents a quasi element in a template literal.
474#[ast(visit)]
475#[derive(Debug, Clone)]
476#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
477#[estree(via = TemplateElementConverter)]
478pub struct TemplateElement<'a> {
479    pub span: Span,
480    pub value: TemplateElementValue<'a>,
481    pub tail: bool,
482    /// The template element contains lone surrogates.
483    ///
484    /// `value.cooked` is encoded using `\u{FFFD}` (the lossy replacement character) as an escape character.
485    /// Lone surrogates are encoded as `\u{FFFD}XXXX`, where `XXXX` is the code unit in hex.
486    /// The lossy escape character itself is encoded as `\u{FFFD}fffd`.
487    #[builder(default)]
488    #[estree(skip)]
489    pub lone_surrogates: bool,
490}
491
492/// See [template-strings-cooked-vs-raw](https://exploringjs.com/js/book/ch_template-literals.html#template-strings-cooked-vs-raw)
493#[ast]
494#[derive(Debug, Clone)]
495#[generate_derive(CloneIn, Dummy, TakeIn, ContentEq, ESTree)]
496#[estree(no_type)]
497pub struct TemplateElementValue<'a> {
498    /// A raw interpretation where backslashes do not have special meaning.
499    /// For example, \t produces two characters – a backslash and a t.
500    /// This interpretation of the template strings is stored in property .raw of the first argument (an Array).
501    pub raw: Atom<'a>,
502    /// A cooked interpretation where backslashes have special meaning.
503    /// For example, \t produces a tab character.
504    /// This interpretation of the template strings is stored as an Array in the first argument.
505    /// cooked = None when template literal has invalid escape sequence
506    pub cooked: Option<Atom<'a>>,
507}
508
509/// Represents a member access expression, which can include computed member access,
510/// static member access, or private field access.
511///
512/// <https://tc39.es/ecma262/#prod-MemberExpression>
513#[ast(visit)]
514#[derive(Debug)]
515#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
516pub enum MemberExpression<'a> {
517    /// `ar[0]` in `const ar = [1, 2]; ar[0];`
518    ComputedMemberExpression(Box<'a, ComputedMemberExpression<'a>>) = 48,
519    /// `console.log` in `console.log('Hello, World!');`
520    StaticMemberExpression(Box<'a, StaticMemberExpression<'a>>) = 49,
521    /// `c.#a` in `class C { #a = 1; }; const c = new C(); c.#a;`
522    PrivateFieldExpression(Box<'a, PrivateFieldExpression<'a>>) = 50,
523}
524
525/// Macro for matching `MemberExpression`'s variants.
526#[macro_export]
527macro_rules! match_member_expression {
528    ($ty:ident) => {
529        $ty::ComputedMemberExpression(_)
530            | $ty::StaticMemberExpression(_)
531            | $ty::PrivateFieldExpression(_)
532    };
533}
534pub use match_member_expression;
535
536/// `ar[0]` in `const ar = [1, 2]; ar[0];`
537///
538/// Represents a computed member access expression, which can include an object and an expression.
539#[ast(visit)]
540#[derive(Debug)]
541#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
542#[estree(rename = "MemberExpression", add_fields(computed = True))]
543pub struct ComputedMemberExpression<'a> {
544    pub span: Span,
545    pub object: Expression<'a>,
546    #[estree(rename = "property")]
547    pub expression: Expression<'a>,
548    pub optional: bool, // for optional chaining
549}
550
551/// `console.log` in `console.log('Hello, World!');`
552///
553/// Represents a static member access expression, which can include an object and a property.
554#[ast(visit)]
555#[derive(Debug)]
556#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
557#[estree(rename = "MemberExpression", add_fields(computed = False))]
558pub struct StaticMemberExpression<'a> {
559    pub span: Span,
560    pub object: Expression<'a>,
561    pub property: IdentifierName<'a>,
562    pub optional: bool, // for optional chaining
563}
564
565/// `c.#a` in `class C { #a = 1; }; const c = new C(); c.#a;`
566///
567/// Represents a private field access expression, which can include an object and a private identifier.
568#[ast(visit)]
569#[derive(Debug)]
570#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
571#[estree(rename = "MemberExpression", add_fields(computed = False))]
572pub struct PrivateFieldExpression<'a> {
573    pub span: Span,
574    pub object: Expression<'a>,
575    #[estree(rename = "property")]
576    pub field: PrivateIdentifier<'a>,
577    pub optional: bool, // for optional chaining
578}
579
580/// `foo()` in `function foo() { return 1; }; foo();`
581///
582/// Represents a call expression, which can include a callee and arguments.
583///
584/// ## Examples
585/// ```ts
586/// //        ___ callee
587/// const x = foo(1, 2)
588///
589/// //            ^^^^ arguments
590/// const y = foo.bar?.(1, 2)
591/// //               ^ optional
592///
593/// const z = foo<number, string>(1, 2)
594/// //            ^^^^^^^^^^^^^^ type_arguments
595/// ```
596#[ast(visit)]
597#[derive(Debug)]
598#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
599pub struct CallExpression<'a> {
600    pub span: Span,
601    pub callee: Expression<'a>,
602    #[ts]
603    pub type_arguments: Option<Box<'a, TSTypeParameterInstantiation<'a>>>,
604    pub arguments: Vec<'a, Argument<'a>>,
605    pub optional: bool, // for optional chaining
606    /// `true` if the call expression is marked with a `/* @__PURE__ */` comment
607    #[builder(default)]
608    #[estree(skip)]
609    pub pure: bool,
610}
611
612/// `new C()` in `class C {}; new C();`
613///
614/// Represents a new expression, which can include a callee and arguments.
615///
616/// ## Example
617/// ```ts
618/// //           callee         arguments
619/// //              ↓↓↓         ↓↓↓↓
620/// const foo = new Foo<number>(1, 2)
621/// //                 ↑↑↑↑↑↑↑↑
622/// //                 type_arguments
623/// ```
624#[ast(visit)]
625#[derive(Debug)]
626#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
627pub struct NewExpression<'a> {
628    pub span: Span,
629    pub callee: Expression<'a>,
630    #[ts]
631    pub type_arguments: Option<Box<'a, TSTypeParameterInstantiation<'a>>>,
632    /// `true` if the new expression is marked with a `/* @__PURE__ */` comment
633    pub arguments: Vec<'a, Argument<'a>>,
634    #[builder(default)]
635    #[estree(skip)]
636    pub pure: bool,
637}
638
639/// `import.meta` in `console.log(import.meta);`
640///
641/// Represents a meta property. The following syntaxes are supported. `import.meta`, `new.target`.
642#[ast(visit)]
643#[derive(Debug)]
644#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
645pub struct MetaProperty<'a> {
646    pub span: Span,
647    pub meta: IdentifierName<'a>,
648    pub property: IdentifierName<'a>,
649}
650
651/// `...[1, 2]` in `const arr = [...[1, 2]];`
652///
653/// Represents a spread element, which can include an argument.
654#[ast(visit)]
655#[derive(Debug)]
656#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
657pub struct SpreadElement<'a> {
658    pub span: Span,
659    /// The expression being spread.
660    pub argument: Expression<'a>,
661}
662
663inherit_variants! {
664/// Argument
665///
666/// Inherits variants from [`Expression`]. See [`ast` module docs] for explanation of inheritance.
667///
668/// [`ast` module docs]: `super`
669#[ast(visit)]
670#[derive(Debug)]
671#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
672pub enum Argument<'a> {
673    /// `...[1, 2]` in `const arr = [...[1, 2]];`
674    SpreadElement(Box<'a, SpreadElement<'a>>) = 64,
675    // `Expression` variants added here by `inherit_variants!` macro
676    @inherit Expression
677}
678}
679
680/// `++i` in `let i = 0; ++i;`
681///
682/// Represents an update expression, which can include an operator and an argument.
683/// The following syntaxes are supported: `++a`, `a++`, `--a`, `a--`.
684#[ast(visit)]
685#[derive(Debug)]
686#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
687pub struct UpdateExpression<'a> {
688    pub span: Span,
689    pub operator: UpdateOperator,
690    pub prefix: bool,
691    pub argument: SimpleAssignmentTarget<'a>,
692}
693
694/// `typeof` in `typeof a === "string"`
695///
696/// Represents a unary expression, which includes an operator and an argument.
697/// The following syntaxes are supported: `+a`, `-a`, `~a`, `!a`, `delete a`, `void a`, `typeof a`.
698#[ast(visit)]
699#[derive(Debug)]
700#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
701#[estree(add_fields(prefix = True))]
702pub struct UnaryExpression<'a> {
703    pub span: Span,
704    pub operator: UnaryOperator,
705    pub argument: Expression<'a>,
706}
707
708/// `1 + 1` in `const two = 1 + 1;`
709///
710/// Represents a binary expression, which include a left expression, an operator, and a right expression.
711#[ast(visit)]
712#[derive(Debug)]
713#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
714pub struct BinaryExpression<'a> {
715    pub span: Span,
716    pub left: Expression<'a>,
717    pub operator: BinaryOperator,
718    pub right: Expression<'a>,
719}
720
721/// `#brand in obj` in `class Foo { #brand; static isFoo(obj) { return #brand in obj; } }`.
722#[ast(visit)]
723#[derive(Debug)]
724#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
725#[estree(rename = "BinaryExpression", add_fields(operator = In), field_order(left, operator, right, span))]
726pub struct PrivateInExpression<'a> {
727    pub span: Span,
728    pub left: PrivateIdentifier<'a>,
729    pub right: Expression<'a>,
730}
731
732/// `||` in `const foo = bar || 2;`
733///
734/// Represents a logical expression, which includes a left expression, an operator, and a right expression.
735/// The following syntaxes are supported: `||`, `&&` and `??`.
736#[ast(visit)]
737#[derive(Debug)]
738#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
739pub struct LogicalExpression<'a> {
740    pub span: Span,
741    pub left: Expression<'a>,
742    pub operator: LogicalOperator,
743    pub right: Expression<'a>,
744}
745
746/// `bar ? 1 : 2` in `const foo = bar ? 1 : 2;`
747///
748/// Represents a conditional expression, which includes a test, a consequent, and an alternate.
749#[ast(visit)]
750#[derive(Debug)]
751#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
752pub struct ConditionalExpression<'a> {
753    pub span: Span,
754    pub test: Expression<'a>,
755    pub consequent: Expression<'a>,
756    pub alternate: Expression<'a>,
757}
758
759/// `foo = 1` in `let foo; foo = 1;`
760///
761/// Represents an assignment expression, which includes an operator, a target, and an expression.
762#[ast(visit)]
763#[derive(Debug)]
764#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
765pub struct AssignmentExpression<'a> {
766    pub span: Span,
767    pub operator: AssignmentOperator,
768    pub left: AssignmentTarget<'a>,
769    pub right: Expression<'a>,
770}
771
772inherit_variants! {
773/// Destructuring Assignment
774///
775/// Inherits variants from [`SimpleAssignmentTarget`] and [`AssignmentTargetPattern`].
776/// See [`ast` module docs] for explanation of inheritance.
777///
778/// [`ast` module docs]: `super`
779#[ast(visit)]
780#[derive(Debug)]
781#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
782pub enum AssignmentTarget<'a> {
783    // `SimpleAssignmentTarget` variants added here by `inherit_variants!` macro
784    @inherit SimpleAssignmentTarget
785    // `AssignmentTargetPattern` variants added here by `inherit_variants!` macro
786    @inherit AssignmentTargetPattern
787}
788}
789
790inherit_variants! {
791/// Simple Assignment Target
792///
793/// Inherits variants from [`MemberExpression`]. See [`ast` module docs] for explanation of inheritance.
794///
795/// [`ast` module docs]: `super`
796#[ast(visit)]
797#[derive(Debug)]
798#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
799pub enum SimpleAssignmentTarget<'a> {
800    AssignmentTargetIdentifier(Box<'a, IdentifierReference<'a>>) = 0,
801    TSAsExpression(Box<'a, TSAsExpression<'a>>) = 1,
802    TSSatisfiesExpression(Box<'a, TSSatisfiesExpression<'a>>) = 2,
803    TSNonNullExpression(Box<'a, TSNonNullExpression<'a>>) = 3,
804    TSTypeAssertion(Box<'a, TSTypeAssertion<'a>>) = 4,
805    // `MemberExpression` variants added here by `inherit_variants!` macro
806    @inherit MemberExpression
807}
808}
809
810/// Macro for matching `AssignmentTarget`'s variants.
811/// Includes `SimpleAssignmentTarget`'s and `AssignmentTargetPattern`'s variants.
812#[macro_export]
813macro_rules! match_assignment_target {
814    ($ty:ident) => {
815        $ty::AssignmentTargetIdentifier(_)
816            | $ty::ComputedMemberExpression(_)
817            | $ty::StaticMemberExpression(_)
818            | $ty::PrivateFieldExpression(_)
819            | $ty::TSAsExpression(_)
820            | $ty::TSSatisfiesExpression(_)
821            | $ty::TSNonNullExpression(_)
822            | $ty::TSTypeAssertion(_)
823            | $ty::ArrayAssignmentTarget(_)
824            | $ty::ObjectAssignmentTarget(_)
825    };
826}
827pub use match_assignment_target;
828
829/// Macro for matching `SimpleAssignmentTarget`'s variants.
830/// Includes `MemberExpression`'s variants
831#[macro_export]
832macro_rules! match_simple_assignment_target {
833    ($ty:ident) => {
834        $ty::AssignmentTargetIdentifier(_)
835            | $ty::ComputedMemberExpression(_)
836            | $ty::StaticMemberExpression(_)
837            | $ty::PrivateFieldExpression(_)
838            | $ty::TSAsExpression(_)
839            | $ty::TSSatisfiesExpression(_)
840            | $ty::TSNonNullExpression(_)
841            | $ty::TSTypeAssertion(_)
842    };
843}
844pub use match_simple_assignment_target;
845
846#[ast(visit)]
847#[derive(Debug)]
848#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
849pub enum AssignmentTargetPattern<'a> {
850    ArrayAssignmentTarget(Box<'a, ArrayAssignmentTarget<'a>>) = 8,
851    ObjectAssignmentTarget(Box<'a, ObjectAssignmentTarget<'a>>) = 9,
852}
853
854/// Macro for matching `AssignmentTargetPattern`'s variants.
855#[macro_export]
856macro_rules! match_assignment_target_pattern {
857    ($ty:ident) => {
858        $ty::ArrayAssignmentTarget(_) | $ty::ObjectAssignmentTarget(_)
859    };
860}
861pub use match_assignment_target_pattern;
862
863/// `[a, b]` in `[a, b] = arr;`
864///
865/// Represents an array assignment target, which can include elements and a rest element.
866#[ast(visit)]
867#[derive(Debug)]
868#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
869#[estree(
870    rename = "ArrayPattern",
871    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
872    field_order(decorators, elements, optional, typeAnnotation, span),
873)]
874pub struct ArrayAssignmentTarget<'a> {
875    pub span: Span,
876    pub elements: Vec<'a, Option<AssignmentTargetMaybeDefault<'a>>>,
877    #[estree(append_to = elements)]
878    pub rest: Option<Box<'a, AssignmentTargetRest<'a>>>,
879}
880
881/// `{ foo }` in `({ foo } = obj);`
882///
883/// Represents an object assignment target, which can include properties and a rest element.
884#[ast(visit)]
885#[derive(Debug)]
886#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
887#[estree(
888    rename = "ObjectPattern",
889    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
890    field_order(decorators, properties, optional, typeAnnotation, span),
891)]
892pub struct ObjectAssignmentTarget<'a> {
893    pub span: Span,
894    pub properties: Vec<'a, AssignmentTargetProperty<'a>>,
895    #[estree(append_to = properties)]
896    pub rest: Option<Box<'a, AssignmentTargetRest<'a>>>,
897}
898
899/// `rest` in `[foo, ...rest] = arr;` or `({foo, ...rest} = obj);`.
900///
901/// Represents rest element in an `ArrayAssignmentTarget` or `ObjectAssignmentTarget`.
902#[ast(visit)]
903#[derive(Debug)]
904#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
905#[estree(
906    rename = "RestElement",
907    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull, value = TsNull),
908    field_order(decorators, target, optional, typeAnnotation, value, span),
909)]
910pub struct AssignmentTargetRest<'a> {
911    pub span: Span,
912    #[estree(rename = "argument")]
913    pub target: AssignmentTarget<'a>,
914}
915
916inherit_variants! {
917/// Assignment Target Maybe Default
918///
919/// Inherits variants from [`AssignmentTarget`]. See [`ast` module docs] for explanation of inheritance.
920///
921/// [`ast` module docs]: `super`
922#[ast(visit)]
923#[derive(Debug)]
924#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
925pub enum AssignmentTargetMaybeDefault<'a> {
926    AssignmentTargetWithDefault(Box<'a, AssignmentTargetWithDefault<'a>>) = 16,
927    // `AssignmentTarget` variants added here by `inherit_variants!` macro
928    @inherit AssignmentTarget
929}
930}
931
932#[ast(visit)]
933#[derive(Debug)]
934#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
935#[estree(
936    rename = "AssignmentPattern",
937    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
938    field_order(decorators, binding, init, optional, typeAnnotation, span),
939)]
940pub struct AssignmentTargetWithDefault<'a> {
941    pub span: Span,
942    #[estree(rename = "left")]
943    pub binding: AssignmentTarget<'a>,
944    #[estree(rename = "right")]
945    pub init: Expression<'a>,
946}
947
948#[ast(visit)]
949#[derive(Debug)]
950#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
951pub enum AssignmentTargetProperty<'a> {
952    AssignmentTargetPropertyIdentifier(Box<'a, AssignmentTargetPropertyIdentifier<'a>>) = 0,
953    AssignmentTargetPropertyProperty(Box<'a, AssignmentTargetPropertyProperty<'a>>) = 1,
954}
955
956/// `foo` in `({ foo } = obj);`
957///
958/// Represents an assignment target property identifier, which includes a binding,
959/// and an optional init expression.
960#[ast(visit)]
961#[derive(Debug)]
962#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
963#[estree(
964    rename = "Property",
965    add_fields(kind = Init, method = False, shorthand = True, computed = False, optional = TsFalse),
966    field_order(kind, binding, init, method, shorthand, computed, optional, span),
967)]
968pub struct AssignmentTargetPropertyIdentifier<'a> {
969    pub span: Span,
970    #[estree(rename = "key")]
971    pub binding: IdentifierReference<'a>,
972    #[estree(rename = "value", via = AssignmentTargetPropertyIdentifierInit)]
973    pub init: Option<Expression<'a>>,
974}
975
976/// `foo: bar` in `({ foo: bar } = obj);`
977///
978/// Represents an assignment target property property, which includes a name and a binding.
979#[ast(visit)]
980#[derive(Debug)]
981#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
982#[estree(
983    rename = "Property",
984    add_fields(kind = Init, method = False, shorthand = False, optional = TsFalse),
985    field_order(kind, name, binding, method, shorthand, computed, optional, span),
986)]
987pub struct AssignmentTargetPropertyProperty<'a> {
988    pub span: Span,
989    /// The property key
990    /// ```ignore
991    /// ({ prop: renamed } = obj)
992    ///    ^^^^
993    /// ```
994    #[estree(rename = "key")]
995    pub name: PropertyKey<'a>,
996    /// The binding part of the property
997    /// ```ignore
998    /// ({ prop: renamed } = obj)
999    ///          ^^^^^^^
1000    /// ```
1001    #[estree(rename = "value")]
1002    pub binding: AssignmentTargetMaybeDefault<'a>,
1003    /// Property was declared with a computed key
1004    pub computed: bool,
1005}
1006
1007/// `a++, b++` in `let a = 1, b = 2; let result = (a++, b++);`
1008///
1009/// Represents a sequence expression.
1010#[ast(visit)]
1011#[derive(Debug)]
1012#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1013pub struct SequenceExpression<'a> {
1014    pub span: Span,
1015    pub expressions: Vec<'a, Expression<'a>>,
1016}
1017
1018/// `super` in `class C extends B { constructor() { super(); } }`
1019///
1020/// Represents a super expression.
1021#[ast(visit)]
1022#[derive(Debug)]
1023#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1024pub struct Super {
1025    pub span: Span,
1026}
1027
1028/// `await` in `await foo();`
1029///
1030/// Represents an await expression, which can include an argument.
1031#[ast(visit)]
1032#[derive(Debug)]
1033#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1034pub struct AwaitExpression<'a> {
1035    pub span: Span,
1036    pub argument: Expression<'a>,
1037}
1038
1039/// `foo?.bar` in `foo?.bar;`
1040///
1041/// Represents a chain expression, which can include an expression.
1042#[ast(visit)]
1043#[derive(Debug)]
1044#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1045pub struct ChainExpression<'a> {
1046    pub span: Span,
1047    pub expression: ChainElement<'a>,
1048}
1049
1050inherit_variants! {
1051/// Chain Element
1052///
1053/// Inherits variants from [`MemberExpression`]. See [`ast` module docs] for explanation of inheritance.
1054///
1055/// [`ast` module docs]: `super`
1056#[ast(visit)]
1057#[derive(Debug)]
1058#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
1059pub enum ChainElement<'a> {
1060    CallExpression(Box<'a, CallExpression<'a>>) = 0,
1061    /// `foo?.baz!` or `foo?.[bar]!`
1062    TSNonNullExpression(Box<'a, TSNonNullExpression<'a>>) = 1,
1063    // `MemberExpression` variants added here by `inherit_variants!` macro
1064    @inherit MemberExpression
1065}
1066}
1067
1068/// `(a + b)` in `const res = (a + b) / c;`
1069///
1070/// Represents a parenthesized expression, which can include an expression.
1071#[ast(visit)]
1072#[derive(Debug)]
1073#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1074#[estree(via = ParenthesizedExpressionConverter)]
1075pub struct ParenthesizedExpression<'a> {
1076    pub span: Span,
1077    pub expression: Expression<'a>,
1078}
1079
1080inherit_variants! {
1081/// Statement
1082///
1083/// Inherits variants from [`Declaration`] and [`ModuleDeclaration`].
1084/// See [`ast` module docs] for explanation of inheritance.
1085///
1086/// [`ast` module docs]: `super`
1087#[ast(visit)]
1088#[derive(Debug)]
1089#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
1090pub enum Statement<'a> {
1091    // Statements
1092    BlockStatement(Box<'a, BlockStatement<'a>>) = 0,
1093    BreakStatement(Box<'a, BreakStatement<'a>>) = 1,
1094    ContinueStatement(Box<'a, ContinueStatement<'a>>) = 2,
1095    DebuggerStatement(Box<'a, DebuggerStatement>) = 3,
1096    DoWhileStatement(Box<'a, DoWhileStatement<'a>>) = 4,
1097    EmptyStatement(Box<'a, EmptyStatement>) = 5,
1098    ExpressionStatement(Box<'a, ExpressionStatement<'a>>) = 6,
1099    ForInStatement(Box<'a, ForInStatement<'a>>) = 7,
1100    ForOfStatement(Box<'a, ForOfStatement<'a>>) = 8,
1101    ForStatement(Box<'a, ForStatement<'a>>) = 9,
1102    IfStatement(Box<'a, IfStatement<'a>>) = 10,
1103    LabeledStatement(Box<'a, LabeledStatement<'a>>) = 11,
1104    ReturnStatement(Box<'a, ReturnStatement<'a>>) = 12,
1105    SwitchStatement(Box<'a, SwitchStatement<'a>>) = 13,
1106    ThrowStatement(Box<'a, ThrowStatement<'a>>) = 14,
1107    TryStatement(Box<'a, TryStatement<'a>>) = 15,
1108    WhileStatement(Box<'a, WhileStatement<'a>>) = 16,
1109    WithStatement(Box<'a, WithStatement<'a>>) = 17,
1110    // `Declaration` variants added here by `inherit_variants!` macro
1111    @inherit Declaration
1112    // `ModuleDeclaration` variants added here by `inherit_variants!` macro
1113    @inherit ModuleDeclaration
1114}
1115}
1116
1117/// `"use strict";` in `"use strict";`
1118///
1119/// Represents a directive statement, which can include a string literal.
1120#[ast(visit)]
1121#[derive(Debug)]
1122#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1123#[estree(rename = "ExpressionStatement")]
1124pub struct Directive<'a> {
1125    pub span: Span,
1126    /// Directive with any escapes unescaped
1127    pub expression: StringLiteral<'a>,
1128    /// Raw content of directive as it appears in source, any escapes left as is
1129    pub directive: Atom<'a>,
1130}
1131
1132/// `#! /usr/bin/env node` in `#! /usr/bin/env node`
1133///
1134/// Represents a hashbang directive, which can include a value.
1135#[ast(visit)]
1136#[derive(Debug)]
1137#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1138pub struct Hashbang<'a> {
1139    pub span: Span,
1140    pub value: Atom<'a>,
1141}
1142
1143/// `{ let foo = 1; }` in `if(true) { let foo = 1; }`
1144///
1145/// Represents a block statement, which can include a body.
1146#[ast(visit)]
1147#[scope]
1148#[derive(Debug)]
1149#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1150pub struct BlockStatement<'a> {
1151    pub span: Span,
1152    pub body: Vec<'a, Statement<'a>>,
1153    pub scope_id: Cell<Option<ScopeId>>,
1154}
1155
1156/// Declarations and the Variable Statement
1157#[ast(visit)]
1158#[derive(Debug)]
1159#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
1160pub enum Declaration<'a> {
1161    VariableDeclaration(Box<'a, VariableDeclaration<'a>>) = 32,
1162    #[visit(args(flags = ScopeFlags::Function))]
1163    FunctionDeclaration(Box<'a, Function<'a>>) = 33,
1164    ClassDeclaration(Box<'a, Class<'a>>) = 34,
1165
1166    TSTypeAliasDeclaration(Box<'a, TSTypeAliasDeclaration<'a>>) = 35,
1167    TSInterfaceDeclaration(Box<'a, TSInterfaceDeclaration<'a>>) = 36,
1168    TSEnumDeclaration(Box<'a, TSEnumDeclaration<'a>>) = 37,
1169    TSModuleDeclaration(Box<'a, TSModuleDeclaration<'a>>) = 38,
1170    TSImportEqualsDeclaration(Box<'a, TSImportEqualsDeclaration<'a>>) = 39,
1171}
1172
1173/// Macro for matching `Declaration`'s variants.
1174#[macro_export]
1175macro_rules! match_declaration {
1176    ($ty:ident) => {
1177        $ty::VariableDeclaration(_)
1178            | $ty::FunctionDeclaration(_)
1179            | $ty::ClassDeclaration(_)
1180            | $ty::TSTypeAliasDeclaration(_)
1181            | $ty::TSInterfaceDeclaration(_)
1182            | $ty::TSEnumDeclaration(_)
1183            | $ty::TSModuleDeclaration(_)
1184            | $ty::TSImportEqualsDeclaration(_)
1185    };
1186}
1187pub use match_declaration;
1188
1189/// `let a;` in `let a; a = 1;`
1190///
1191/// Represents a variable declaration, which can include a kind, declarations, and modifiers.
1192#[ast(visit)]
1193#[derive(Debug)]
1194#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1195pub struct VariableDeclaration<'a> {
1196    pub span: Span,
1197    pub kind: VariableDeclarationKind,
1198    pub declarations: Vec<'a, VariableDeclarator<'a>>,
1199    #[ts]
1200    pub declare: bool,
1201}
1202
1203#[ast]
1204#[derive(Debug, Clone, Copy, PartialEq, Eq)]
1205#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
1206pub enum VariableDeclarationKind {
1207    Var = 0,
1208    Let = 1,
1209    Const = 2,
1210    Using = 3,
1211    #[estree(rename = "await using")]
1212    AwaitUsing = 4,
1213}
1214
1215/// A single variable declaration in a list of [variable declarations](VariableDeclaration).
1216///
1217/// ## Examples
1218/// ```ts
1219/// // declarators may or may not have initializers
1220/// let foo, b = 1;
1221/// //  ^^^ id   ^ init
1222/// ```
1223#[ast(visit)]
1224#[derive(Debug)]
1225#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1226pub struct VariableDeclarator<'a> {
1227    pub span: Span,
1228    #[estree(skip)]
1229    pub kind: VariableDeclarationKind,
1230    pub id: BindingPattern<'a>,
1231    pub init: Option<Expression<'a>>,
1232    #[ts]
1233    pub definite: bool,
1234}
1235
1236/// Empty Statement
1237#[ast(visit)]
1238#[derive(Debug)]
1239#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1240pub struct EmptyStatement {
1241    pub span: Span,
1242}
1243
1244/// Expression Statement
1245#[ast(visit)]
1246#[derive(Debug)]
1247#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1248#[estree(add_fields(directive = ExpressionStatementDirective))] // Only in TS AST
1249pub struct ExpressionStatement<'a> {
1250    pub span: Span,
1251    pub expression: Expression<'a>,
1252}
1253
1254/// If Statement
1255#[ast(visit)]
1256#[derive(Debug)]
1257#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1258pub struct IfStatement<'a> {
1259    pub span: Span,
1260    pub test: Expression<'a>,
1261    pub consequent: Statement<'a>,
1262    pub alternate: Option<Statement<'a>>,
1263}
1264
1265/// Do-While Statement
1266#[ast(visit)]
1267#[derive(Debug)]
1268#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1269pub struct DoWhileStatement<'a> {
1270    pub span: Span,
1271    pub body: Statement<'a>,
1272    pub test: Expression<'a>,
1273}
1274
1275/// While Statement
1276#[ast(visit)]
1277#[derive(Debug)]
1278#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1279pub struct WhileStatement<'a> {
1280    pub span: Span,
1281    pub test: Expression<'a>,
1282    pub body: Statement<'a>,
1283}
1284
1285/// For Statement
1286#[ast(visit)]
1287#[scope]
1288#[derive(Debug)]
1289#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1290pub struct ForStatement<'a> {
1291    pub span: Span,
1292    pub init: Option<ForStatementInit<'a>>,
1293    pub test: Option<Expression<'a>>,
1294    pub update: Option<Expression<'a>>,
1295    pub body: Statement<'a>,
1296    pub scope_id: Cell<Option<ScopeId>>,
1297}
1298
1299inherit_variants! {
1300/// For Statement Init
1301///
1302/// Inherits variants from [`Expression`]. See [`ast` module docs] for explanation of inheritance.
1303///
1304/// [`ast` module docs]: `super`
1305#[ast(visit)]
1306#[derive(Debug)]
1307#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
1308pub enum ForStatementInit<'a> {
1309    VariableDeclaration(Box<'a, VariableDeclaration<'a>>) = 64,
1310    // `Expression` variants added here by `inherit_variants!` macro
1311    @inherit Expression
1312}
1313}
1314
1315/// For-In Statement
1316#[ast(visit)]
1317#[scope]
1318#[derive(Debug)]
1319#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1320pub struct ForInStatement<'a> {
1321    pub span: Span,
1322    pub left: ForStatementLeft<'a>,
1323    pub right: Expression<'a>,
1324    pub body: Statement<'a>,
1325    pub scope_id: Cell<Option<ScopeId>>,
1326}
1327
1328inherit_variants! {
1329/// For Statement Left
1330///
1331/// Inherits variants from [`AssignmentTarget`]. See [`ast` module docs] for explanation of inheritance.
1332///
1333/// [`ast` module docs]: `super`
1334#[ast(visit)]
1335#[derive(Debug)]
1336#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
1337pub enum ForStatementLeft<'a> {
1338    VariableDeclaration(Box<'a, VariableDeclaration<'a>>) = 16,
1339    // `AssignmentTarget` variants added here by `inherit_variants!` macro
1340    @inherit AssignmentTarget
1341}
1342}
1343
1344/// For-Of Statement
1345#[ast(visit)]
1346#[scope]
1347#[derive(Debug)]
1348#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1349pub struct ForOfStatement<'a> {
1350    pub span: Span,
1351    pub r#await: bool,
1352    pub left: ForStatementLeft<'a>,
1353    pub right: Expression<'a>,
1354    pub body: Statement<'a>,
1355    pub scope_id: Cell<Option<ScopeId>>,
1356}
1357
1358/// Continue Statement
1359#[ast(visit)]
1360#[derive(Debug)]
1361#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1362pub struct ContinueStatement<'a> {
1363    pub span: Span,
1364    pub label: Option<LabelIdentifier<'a>>,
1365}
1366
1367/// Break Statement
1368#[ast(visit)]
1369#[derive(Debug)]
1370#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1371pub struct BreakStatement<'a> {
1372    pub span: Span,
1373    pub label: Option<LabelIdentifier<'a>>,
1374}
1375
1376/// Return Statement
1377#[ast(visit)]
1378#[derive(Debug)]
1379#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1380pub struct ReturnStatement<'a> {
1381    pub span: Span,
1382    pub argument: Option<Expression<'a>>,
1383}
1384
1385/// With Statement
1386#[ast(visit)]
1387#[derive(Debug)]
1388#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1389pub struct WithStatement<'a> {
1390    pub span: Span,
1391    pub object: Expression<'a>,
1392    pub body: Statement<'a>,
1393}
1394
1395/// Switch Statement
1396#[ast(visit)]
1397#[scope]
1398#[derive(Debug)]
1399#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1400pub struct SwitchStatement<'a> {
1401    pub span: Span,
1402    pub discriminant: Expression<'a>,
1403    #[scope(enter_before)]
1404    pub cases: Vec<'a, SwitchCase<'a>>,
1405    pub scope_id: Cell<Option<ScopeId>>,
1406}
1407
1408#[ast(visit)]
1409#[derive(Debug)]
1410#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1411pub struct SwitchCase<'a> {
1412    pub span: Span,
1413    pub test: Option<Expression<'a>>,
1414    pub consequent: Vec<'a, Statement<'a>>,
1415}
1416
1417/// Labelled Statement
1418#[ast(visit)]
1419#[derive(Debug)]
1420#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1421pub struct LabeledStatement<'a> {
1422    pub span: Span,
1423    pub label: LabelIdentifier<'a>,
1424    pub body: Statement<'a>,
1425}
1426
1427/// Throw Statement
1428///
1429/// # Example
1430/// ```ts
1431/// throw new Error('something went wrong!');
1432/// //    ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ argument
1433/// ```
1434#[ast(visit)]
1435#[derive(Debug)]
1436#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1437pub struct ThrowStatement<'a> {
1438    pub span: Span,
1439    /// The expression being thrown, e.g. `err` in `throw err;`
1440    pub argument: Expression<'a>,
1441}
1442
1443/// Try Statement
1444///
1445/// # Example
1446/// ```ts
1447/// var x;
1448/// let didRun = false;
1449///
1450/// try {                 // block
1451///     x = 1;
1452/// } catch (e) {         // handler
1453///     console.error(e);
1454/// } finally {           // finalizer
1455///     didRun = true;
1456/// }
1457/// ```
1458#[ast(visit)]
1459#[derive(Debug)]
1460#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1461pub struct TryStatement<'a> {
1462    pub span: Span,
1463    /// Statements in the `try` block
1464    pub block: Box<'a, BlockStatement<'a>>,
1465    /// The `catch` clause, including the parameter and the block statement
1466    pub handler: Option<Box<'a, CatchClause<'a>>>,
1467    /// The `finally` clause
1468    pub finalizer: Option<Box<'a, BlockStatement<'a>>>,
1469}
1470
1471/// Catch Clause in a [`try/catch` statement](TryStatement).
1472///
1473/// This node creates a new scope inside its `body`.
1474///
1475/// # Example
1476/// ```ts
1477/// try {
1478///   throw new Error('foo');
1479/// } catch (e) {             // `param` is `e`
1480///   console.error(e);       // `body`
1481/// }
1482/// ```
1483#[ast(visit)]
1484#[scope(flags = ScopeFlags::CatchClause)]
1485#[derive(Debug)]
1486#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1487pub struct CatchClause<'a> {
1488    pub span: Span,
1489    /// The caught error parameter, e.g. `e` in `catch (e) {}`
1490    pub param: Option<CatchParameter<'a>>,
1491    /// The statements run when an error is caught
1492    pub body: Box<'a, BlockStatement<'a>>,
1493    pub scope_id: Cell<Option<ScopeId>>,
1494}
1495
1496/// A caught error parameter in a [catch clause](CatchClause).
1497///
1498/// # Examples
1499///
1500/// ```ts
1501/// try {} catch (err) {}
1502/// //            ^^^ pattern
1503/// ```
1504///
1505/// ```ts
1506/// try {} catch ({ err }) {}
1507/// //            ^^^^^^^  pattern
1508/// ```
1509#[ast(visit)]
1510#[derive(Debug)]
1511#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1512#[estree(no_type, via = CatchParameterConverter)]
1513pub struct CatchParameter<'a> {
1514    #[estree(skip)]
1515    pub span: Span,
1516    /// The bound error
1517    #[estree(flatten)]
1518    pub pattern: BindingPattern<'a>,
1519}
1520
1521/// Debugger Statement
1522///
1523/// # Example
1524/// ```ts
1525/// let x = 1;
1526/// debugger; // <--
1527/// ```
1528#[ast(visit)]
1529#[derive(Debug)]
1530#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1531pub struct DebuggerStatement {
1532    pub span: Span,
1533}
1534
1535/// Destructuring Binding Patterns.
1536/// <https://tc39.es/ecma262/#prod-BindingPattern>
1537///
1538/// Binding patterns can be nested within other binding patterns
1539/// e.g. `const [ { a: [ {x} ] } ] = arr;`.
1540///
1541/// Type annotations are valid in some positions e.g. `const x: T = f();`
1542/// but invalid in others e.g. `const [x: T] = f();`.
1543#[ast(visit)]
1544#[derive(Debug)]
1545#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1546#[estree(no_type, via = BindingPatternConverter, field_order(kind, optional, type_annotation))]
1547pub struct BindingPattern<'a> {
1548    // estree(flatten) the attributes because estree has no `BindingPattern`
1549    #[estree(
1550        flatten,
1551        ts_type = "(BindingIdentifier | ObjectPattern | ArrayPattern | AssignmentPattern)"
1552    )]
1553    #[span]
1554    pub kind: BindingPatternKind<'a>,
1555    #[ts]
1556    pub type_annotation: Option<Box<'a, TSTypeAnnotation<'a>>>,
1557    #[ts]
1558    pub optional: bool,
1559}
1560
1561#[ast(visit)]
1562#[derive(Debug)]
1563#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
1564pub enum BindingPatternKind<'a> {
1565    /// `x` in `const x = 1;`.
1566    ///
1567    /// Also e.g. `x` in:
1568    /// - `const [x] = arr;`
1569    /// - `const { a: x } = obj;`
1570    /// - `const [ ...x ] = arr;`
1571    /// - `const [x = 1] = arr;`
1572    /// - `function f(x) {}`
1573    /// - `try {} catch (x) {}`
1574    BindingIdentifier(Box<'a, BindingIdentifier<'a>>) = 0,
1575    /// `{x}` in `const {x} = 1;`.
1576    ///
1577    /// Also e.g. `{x}` in:
1578    /// - `const [{x}] = arr;`
1579    /// - `const { a: {x} } = obj;`
1580    /// - `const [{x} = obj] = arr;`
1581    /// - `const [ ...{x} ] = arr;`
1582    /// - `function f({x}) {}`
1583    /// - `try {} catch ({x}) {}`
1584    ObjectPattern(Box<'a, ObjectPattern<'a>>) = 1,
1585    /// `[x]` in `const [x] = 1;`
1586    ///
1587    /// Also e.g. `[x]` in:
1588    /// - `const { a: [x] } = obj;`
1589    /// - `const { a: [x] = arr } = obj;`
1590    /// - `const [[x]] = obj;`
1591    /// - `const [ ...[x] ] = arr;`
1592    /// - `function f([x]) {}`
1593    /// - `try {} catch ([x]) {}`
1594    ArrayPattern(Box<'a, ArrayPattern<'a>>) = 2,
1595    /// `x = 1` in `const {x = 1} = obj;`.
1596    ///
1597    /// Also e.g. `x = 1` in:
1598    /// - `const [x = 1] = arr;`
1599    /// - `const { a: x = 1 } = obj;`
1600    /// - `function f(x = 1) {}`
1601    ///
1602    /// Also e.g. `{x} = obj` in:
1603    /// - `const [{x} = obj] = arr;`
1604    /// - `const { a: {x} = obj2 } = obj;`
1605    /// - `function f({x} = obj) {}`
1606    ///
1607    /// Invalid in:
1608    /// - `BindingRestElement` e.g. `const [...x = 1] = arr;`.
1609    /// - `CatchParameter` e.g. `try {} catch (e = 1) {}`.
1610    AssignmentPattern(Box<'a, AssignmentPattern<'a>>) = 3,
1611}
1612
1613/// `x = 1` in `const {x = 1} = obj;`.
1614///
1615/// See other examples in docs for [`BindingPatternKind`].
1616#[ast(visit)]
1617#[derive(Debug)]
1618#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1619#[estree(
1620    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
1621    field_order(decorators, left, right, optional, typeAnnotation, span),
1622)]
1623pub struct AssignmentPattern<'a> {
1624    pub span: Span,
1625    pub left: BindingPattern<'a>,
1626    pub right: Expression<'a>,
1627}
1628
1629/// `{x}` in `const {x} = 1;`.
1630///
1631/// See other examples in docs for [`BindingPatternKind`].
1632#[ast(visit)]
1633#[derive(Debug)]
1634#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1635#[estree(
1636    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
1637    field_order(decorators, properties, optional, typeAnnotation, span),
1638)]
1639pub struct ObjectPattern<'a> {
1640    pub span: Span,
1641    pub properties: Vec<'a, BindingProperty<'a>>,
1642    #[estree(append_to = properties)]
1643    pub rest: Option<Box<'a, BindingRestElement<'a>>>,
1644}
1645
1646#[ast(visit)]
1647#[derive(Debug)]
1648#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1649#[estree(
1650    rename = "Property",
1651    add_fields(kind = Init, method = False, optional = TsFalse),
1652    field_order(kind, key, value, method, shorthand, computed, optional, span),
1653)]
1654pub struct BindingProperty<'a> {
1655    pub span: Span,
1656    pub key: PropertyKey<'a>,
1657    pub value: BindingPattern<'a>,
1658    pub shorthand: bool,
1659    pub computed: bool,
1660}
1661
1662/// `[x]` in `const [x] = 1;`
1663///
1664/// See other examples in docs for [`BindingPatternKind`].
1665#[ast(visit)]
1666#[derive(Debug)]
1667#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1668#[estree(
1669    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull),
1670    field_order(decorators, elements, optional, typeAnnotation, span),
1671)]
1672pub struct ArrayPattern<'a> {
1673    pub span: Span,
1674    pub elements: Vec<'a, Option<BindingPattern<'a>>>,
1675    #[estree(append_to = elements)]
1676    pub rest: Option<Box<'a, BindingRestElement<'a>>>,
1677}
1678
1679/// A `...rest` binding in an [array](ArrayPattern) or [object](ObjectPattern) destructure.
1680///
1681/// ## Examples
1682/// ```ts
1683/// const [a, ...rest] = [1, 2, 3];
1684/// //           ^^^^  argument
1685/// const { x, y, ...others} = foo.bar();
1686/// //               ^^^^^^  argument
1687/// ```
1688#[ast(visit)]
1689#[derive(Debug)]
1690#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1691#[estree(
1692    rename = "RestElement",
1693    add_fields(decorators = TsEmptyArray, optional = TsFalse, typeAnnotation = TsNull, value = TsNull),
1694    field_order(decorators, argument, optional, typeAnnotation, value, span),
1695)]
1696pub struct BindingRestElement<'a> {
1697    pub span: Span,
1698    pub argument: BindingPattern<'a>,
1699}
1700
1701/// Function Statement or Expression
1702///
1703/// Includes generator functions and function-valued class properties.
1704/// Arrow functions are represented by [`ArrowFunctionExpression`].
1705///
1706/// # Examples
1707/// ```ts
1708/// //    id ___             ____ return_type
1709/// function foo(a: number): void {
1710/// //           ^^^^^^^^^ params
1711///     console.log(a);
1712/// }
1713/// ```
1714///
1715/// ```ts
1716/// // `async` and `generator` are true
1717/// async function* foo() {
1718///     yield 1;
1719/// }
1720/// ```
1721///
1722/// ```js
1723/// // function.id is None
1724/// // use function.r#type to check if a node is a function expression.
1725/// const foo = function() { }
1726/// ```
1727///
1728/// ```ts
1729/// // Function overloads will not have a body
1730/// function add(a: number, b: number): number; // <-- No body
1731/// function add(a: string, b: string): string; // <-- No body
1732/// function add(a: any, b: any): any {         // <-- Body is between `{}`, inclusive.
1733///    return a + b;
1734/// }
1735/// ```
1736#[ast(visit)]
1737#[visit(args(flags = ScopeFlags))]
1738#[scope(
1739    // `flags` passed in to visitor via parameter defined by `#[visit(args(flags = ...))]` on parents
1740    flags = flags,
1741    strict_if = self.has_use_strict_directive(),
1742)]
1743#[derive(Debug)]
1744#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1745// https://github.com/estree/estree/blob/master/es5.md#patterns
1746// https://github.com/DefinitelyTyped/DefinitelyTyped/blob/cd61c555bfc93e985b313263a42ed78074570d08/types/estree/index.d.ts#L411
1747#[estree(
1748    add_ts_def = "type ParamPattern = FormalParameter | TSParameterProperty | FormalParameterRest",
1749    add_fields(expression = False),
1750)]
1751pub struct Function<'a> {
1752    pub span: Span,
1753    pub r#type: FunctionType,
1754    /// The function identifier. [`None`] for anonymous function expressions.
1755    pub id: Option<BindingIdentifier<'a>>,
1756    /// Is this a generator function?
1757    ///
1758    /// ```ts
1759    /// function* foo() { } // <- generator: true
1760    /// function bar() { }  // <- generator: false
1761    /// ```
1762    pub generator: bool,
1763    pub r#async: bool,
1764    #[ts]
1765    pub declare: bool,
1766    #[ts]
1767    pub type_parameters: Option<Box<'a, TSTypeParameterDeclaration<'a>>>,
1768    /// Declaring `this` in a Function <https://www.typescriptlang.org/docs/handbook/2/functions.html#declaring-this-in-a-function>
1769    ///
1770    /// The JavaScript specification states that you cannot have a parameter called `this`,
1771    /// and so TypeScript uses that syntax space to let you declare the type for `this` in the function body.
1772    ///
1773    /// ```ts
1774    /// interface DB {
1775    ///     filterUsers(filter: (this: User) => boolean): User[];
1776    ///     //                   ^^^^
1777    /// }
1778    ///
1779    /// const db = getDB();
1780    /// const admins = db.filterUsers(function (this: User) {
1781    ///     return this.admin;
1782    /// });
1783    /// ```
1784    #[ts]
1785    #[estree(skip)]
1786    pub this_param: Option<Box<'a, TSThisParameter<'a>>>,
1787    /// Function parameters.
1788    ///
1789    /// Does not include `this` parameters used by some TypeScript functions.
1790    #[estree(via = FunctionParams)]
1791    pub params: Box<'a, FormalParameters<'a>>,
1792    /// The TypeScript return type annotation.
1793    #[ts]
1794    pub return_type: Option<Box<'a, TSTypeAnnotation<'a>>>,
1795    /// The function body.
1796    ///
1797    /// [`None`] for function declarations, e.g.
1798    /// ```ts
1799    /// // TypeScript function declarations have no body
1800    /// declare function foo(a: number): number;
1801    ///
1802    /// function bar(a: number): number; // <- overloads have no body
1803    /// function bar(a: number): number {
1804    ///     return a;
1805    /// }
1806    /// ```
1807    pub body: Option<Box<'a, FunctionBody<'a>>>,
1808    pub scope_id: Cell<Option<ScopeId>>,
1809    /// `true` if the function is marked with a `/*#__NO_SIDE_EFFECTS__*/` comment
1810    #[builder(default)]
1811    #[estree(skip)]
1812    pub pure: bool,
1813    #[builder(default)]
1814    #[estree(skip)]
1815    /// `true` if the function should be marked as "Possibly-Invoked Function Expression" (PIFE).
1816    ///
1817    /// This only affects FunctionExpressions.
1818    ///
1819    /// References:
1820    /// - v8 blog post about PIFEs: <https://v8.dev/blog/preparser#pife>
1821    /// - related PR: <https://github.com/oxc-project/oxc/pull/12353>
1822    pub pife: bool,
1823}
1824
1825#[ast]
1826#[derive(Debug, Clone, Copy, PartialEq, Eq)]
1827#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
1828#[estree(no_rename_variants)]
1829pub enum FunctionType {
1830    FunctionDeclaration = 0,
1831    FunctionExpression = 1,
1832    TSDeclareFunction = 2,
1833    /// <https://github.com/typescript-eslint/typescript-eslint/pull/1289>
1834    TSEmptyBodyFunctionExpression = 3,
1835}
1836
1837/// <https://tc39.es/ecma262/#prod-FormalParameters>
1838#[ast(visit)]
1839#[derive(Debug)]
1840#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1841#[estree(
1842    via = FormalParametersConverter,
1843    add_ts_def = "
1844        interface FormalParameterRest extends Span {
1845            type: 'RestElement';
1846            argument: BindingPatternKind;
1847            decorators?: [],
1848            optional?: boolean;
1849            typeAnnotation?: TSTypeAnnotation | null;
1850            value?: null;
1851        }
1852    "
1853)]
1854pub struct FormalParameters<'a> {
1855    pub span: Span,
1856    pub kind: FormalParameterKind,
1857    #[estree(ts_type = "Array<FormalParameter | TSParameterProperty | FormalParameterRest>")]
1858    pub items: Vec<'a, FormalParameter<'a>>,
1859    #[estree(skip)]
1860    pub rest: Option<Box<'a, BindingRestElement<'a>>>,
1861}
1862
1863#[ast(visit)]
1864#[derive(Debug)]
1865#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1866// Pluralize as `FormalParameterList` to avoid naming clash with `FormalParameters`.
1867#[plural(FormalParameterList)]
1868#[estree(
1869    no_type,
1870    via = FormalParameterConverter,
1871    add_ts_def = "
1872        type FormalParameter =
1873            & ({
1874                decorators?: Array<Decorator>;
1875            })
1876            & BindingPattern;
1877
1878        export interface TSParameterProperty extends Span {
1879            type: 'TSParameterProperty';
1880            accessibility: TSAccessibility | null;
1881            decorators: Array<Decorator>;
1882            override: boolean;
1883            parameter: FormalParameter;
1884            readonly: boolean;
1885            static: boolean;
1886        }
1887    "
1888)]
1889pub struct FormalParameter<'a> {
1890    #[estree(skip)]
1891    pub span: Span,
1892    #[ts]
1893    pub decorators: Vec<'a, Decorator<'a>>,
1894    #[estree(flatten)]
1895    pub pattern: BindingPattern<'a>,
1896    #[ts]
1897    #[estree(skip)]
1898    pub accessibility: Option<TSAccessibility>,
1899    #[ts]
1900    #[estree(skip)]
1901    pub readonly: bool,
1902    #[ts]
1903    #[estree(skip)]
1904    pub r#override: bool,
1905}
1906
1907#[ast]
1908#[derive(Debug, Clone, Copy, PartialEq, Eq)]
1909#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
1910#[estree(no_rename_variants, no_ts_def)]
1911pub enum FormalParameterKind {
1912    /// <https://tc39.es/ecma262/#prod-FormalParameters>
1913    FormalParameter = 0,
1914    /// <https://tc39.es/ecma262/#prod-UniqueFormalParameters>
1915    UniqueFormalParameters = 1,
1916    /// <https://tc39.es/ecma262/#prod-ArrowFormalParameters>
1917    ArrowFormalParameters = 2,
1918    /// Part of TypeScript type signatures
1919    Signature = 3,
1920}
1921
1922/// <https://tc39.es/ecma262/#prod-FunctionBody>
1923#[ast(visit)]
1924#[derive(Debug)]
1925#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1926#[estree(rename = "BlockStatement")]
1927pub struct FunctionBody<'a> {
1928    pub span: Span,
1929    #[estree(prepend_to = statements)]
1930    pub directives: Vec<'a, Directive<'a>>,
1931    #[estree(rename = "body")]
1932    pub statements: Vec<'a, Statement<'a>>,
1933}
1934
1935/// Arrow Function Definitions
1936#[ast(visit)]
1937#[scope(
1938    flags = ScopeFlags::Function | ScopeFlags::Arrow,
1939    strict_if = self.has_use_strict_directive(),
1940)]
1941#[derive(Debug)]
1942#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1943#[estree(add_fields(id = Null, generator = False))]
1944pub struct ArrowFunctionExpression<'a> {
1945    pub span: Span,
1946    /// Is the function body an arrow expression? i.e. `() => expr` instead of `() => {}`
1947    pub expression: bool,
1948    pub r#async: bool,
1949    #[ts]
1950    pub type_parameters: Option<Box<'a, TSTypeParameterDeclaration<'a>>>,
1951    pub params: Box<'a, FormalParameters<'a>>,
1952    #[ts]
1953    pub return_type: Option<Box<'a, TSTypeAnnotation<'a>>>,
1954    /// See `expression` for whether this arrow expression returns an expression.
1955    // ESTree: https://github.com/estree/estree/blob/master/es2015.md#arrowfunctionexpression
1956    #[estree(via = ArrowFunctionExpressionBody)]
1957    pub body: Box<'a, FunctionBody<'a>>,
1958    pub scope_id: Cell<Option<ScopeId>>,
1959    /// `true` if the function is marked with a `/*#__NO_SIDE_EFFECTS__*/` comment
1960    #[builder(default)]
1961    #[estree(skip)]
1962    pub pure: bool,
1963    #[builder(default)]
1964    #[estree(skip)]
1965    /// `true` if the function should be marked as "Possibly-Invoked Function Expression" (PIFE).
1966    ///
1967    /// References:
1968    /// - v8 blog post about PIFEs: <https://v8.dev/blog/preparser#pife>
1969    /// - introduced PR: <https://github.com/oxc-project/oxc/pull/12353>
1970    pub pife: bool,
1971}
1972
1973/// Generator Function Definitions
1974#[ast(visit)]
1975#[derive(Debug)]
1976#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1977pub struct YieldExpression<'a> {
1978    pub span: Span,
1979    pub delegate: bool,
1980    pub argument: Option<Expression<'a>>,
1981}
1982
1983/// Class Definitions
1984#[ast(visit)]
1985#[scope(flags = ScopeFlags::StrictMode)]
1986#[derive(Debug)]
1987#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
1988pub struct Class<'a> {
1989    pub span: Span,
1990    pub r#type: ClassType,
1991    /// Decorators applied to the class.
1992    ///
1993    /// Decorators are currently a stage 3 proposal. Oxc handles both TC39 and
1994    /// legacy TypeScript decorators.
1995    ///
1996    /// ## Example
1997    /// ```ts
1998    /// @Bar() // <-- Decorator
1999    /// class Foo {}
2000    /// ```
2001    pub decorators: Vec<'a, Decorator<'a>>,
2002    /// Class identifier, AKA the name
2003    pub id: Option<BindingIdentifier<'a>>,
2004    #[scope(enter_before)]
2005    #[ts]
2006    pub type_parameters: Option<Box<'a, TSTypeParameterDeclaration<'a>>>,
2007    /// Super class. When present, this will usually be an [`IdentifierReference`].
2008    ///
2009    /// ## Example
2010    /// ```ts
2011    /// class Foo extends Bar {}
2012    /// //                ^^^
2013    /// ```
2014    pub super_class: Option<Expression<'a>>,
2015    /// Type parameters passed to super class.
2016    ///
2017    /// ## Example
2018    /// ```ts
2019    /// class Foo<T> extends Bar<T> {}
2020    /// //                       ^
2021    /// ```
2022    #[ts]
2023    pub super_type_arguments: Option<Box<'a, TSTypeParameterInstantiation<'a>>>,
2024    /// Interface implementation clause for TypeScript classes.
2025    ///
2026    /// ## Example
2027    /// ```ts
2028    /// interface Bar {}
2029    /// class Foo implements Bar {}
2030    /// //                   ^^^
2031    /// ```
2032    #[ts]
2033    pub implements: Vec<'a, TSClassImplements<'a>>,
2034    pub body: Box<'a, ClassBody<'a>>,
2035    /// Whether the class is abstract
2036    ///
2037    /// ## Example
2038    /// ```ts
2039    /// class Foo {}          // true
2040    /// abstract class Bar {} // false
2041    /// ```
2042    #[ts]
2043    pub r#abstract: bool,
2044    /// Whether the class was `declare`ed
2045    ///
2046    /// ## Example
2047    /// ```ts
2048    /// declare class Foo {}
2049    /// ```
2050    #[ts]
2051    pub declare: bool,
2052    /// Id of the scope created by the [`Class`], including type parameters and
2053    /// statements within the [`ClassBody`].
2054    pub scope_id: Cell<Option<ScopeId>>,
2055}
2056
2057#[ast]
2058#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2059#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
2060#[estree(no_rename_variants)]
2061pub enum ClassType {
2062    /// Class declaration statement
2063    /// ```ts
2064    /// class Foo { }
2065    /// ```
2066    ClassDeclaration = 0,
2067    /// Class expression
2068    ///
2069    /// ```ts
2070    /// const Foo = class {}
2071    /// ```
2072    ClassExpression = 1,
2073}
2074
2075#[ast(visit)]
2076#[derive(Debug)]
2077#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2078pub struct ClassBody<'a> {
2079    pub span: Span,
2080    pub body: Vec<'a, ClassElement<'a>>,
2081}
2082
2083/// Class Body Element
2084///
2085/// ## Example
2086/// ```ts
2087/// class Foo {
2088///   [prop: string]: string // ClassElement::TSIndexSignature
2089///
2090///   public x: number // ClassElement::PropertyDefinition
2091///
2092///   accessor z() { return 5 } // ClassElement::AccessorProperty
2093///
2094///   // These are all ClassElement::MethodDefinitions
2095///   get y() { return 5 }
2096///   set y(value) { }
2097///   static foo() {}
2098///   bar() {}
2099/// }
2100/// ```
2101#[ast(visit)]
2102#[derive(Debug)]
2103#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
2104pub enum ClassElement<'a> {
2105    StaticBlock(Box<'a, StaticBlock<'a>>) = 0,
2106    /// Class Methods
2107    ///
2108    /// Includes static and non-static methods, constructors, getters, and setters.
2109    MethodDefinition(Box<'a, MethodDefinition<'a>>) = 1,
2110    PropertyDefinition(Box<'a, PropertyDefinition<'a>>) = 2,
2111    AccessorProperty(Box<'a, AccessorProperty<'a>>) = 3,
2112    /// Index Signature
2113    ///
2114    /// ## Example
2115    /// ```ts
2116    /// class Foo {
2117    ///   [keys: string]: string
2118    /// }
2119    /// ```
2120    TSIndexSignature(Box<'a, TSIndexSignature<'a>>) = 4,
2121}
2122
2123#[ast(visit)]
2124#[derive(Debug)]
2125#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2126pub struct MethodDefinition<'a> {
2127    pub span: Span,
2128    /// Method definition type
2129    ///
2130    /// This will always be true when an `abstract` modifier is used on the method.
2131    pub r#type: MethodDefinitionType,
2132    pub decorators: Vec<'a, Decorator<'a>>,
2133    pub key: PropertyKey<'a>,
2134    #[visit(args(flags = match self.kind {
2135        MethodDefinitionKind::Get => ScopeFlags::Function | ScopeFlags::GetAccessor,
2136        MethodDefinitionKind::Set => ScopeFlags::Function | ScopeFlags::SetAccessor,
2137        MethodDefinitionKind::Constructor => ScopeFlags::Function | ScopeFlags::Constructor,
2138        MethodDefinitionKind::Method => ScopeFlags::Function,
2139    }))]
2140    pub value: Box<'a, Function<'a>>, // FunctionExpression
2141    pub kind: MethodDefinitionKind,
2142    pub computed: bool,
2143    pub r#static: bool,
2144    #[ts]
2145    pub r#override: bool,
2146    #[ts]
2147    pub optional: bool,
2148    #[ts]
2149    pub accessibility: Option<TSAccessibility>,
2150}
2151
2152#[ast]
2153#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2154#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
2155#[estree(no_rename_variants)]
2156pub enum MethodDefinitionType {
2157    MethodDefinition = 0,
2158    TSAbstractMethodDefinition = 1,
2159}
2160
2161#[ast(visit)]
2162#[derive(Debug)]
2163#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2164pub struct PropertyDefinition<'a> {
2165    pub span: Span,
2166    pub r#type: PropertyDefinitionType,
2167    /// Decorators applied to the property.
2168    ///
2169    /// See [`Decorator`] for more information.
2170    pub decorators: Vec<'a, Decorator<'a>>,
2171    /// The expression used to declare the property.
2172    pub key: PropertyKey<'a>,
2173    /// Type annotation on the property.
2174    ///
2175    /// e.g. `class Foo { x: number; }`
2176    ///
2177    /// Will only ever be [`Some`] for TypeScript files.
2178    #[ts]
2179    pub type_annotation: Option<Box<'a, TSTypeAnnotation<'a>>>,
2180    /// Initialized value in the declaration.
2181    ///
2182    /// ## Example
2183    /// ```ts
2184    /// class Foo {
2185    ///   x = 5;     // Some(NumericLiteral)
2186    ///   y;         // None
2187    ///   z: string; // None
2188    ///
2189    ///   constructor() {
2190    ///     this.z = "hello";
2191    ///   }
2192    /// }
2193    /// ```
2194    pub value: Option<Expression<'a>>,
2195    /// Property was declared with a computed key
2196    ///
2197    /// ## Example
2198    /// ```js
2199    /// class Foo {
2200    ///   ["a"]: 1; // true
2201    ///   b: 2;     // false
2202    /// }
2203    /// ```
2204    pub computed: bool,
2205    /// Property was declared with a `static` modifier
2206    pub r#static: bool,
2207    /// Property is declared with a `declare` modifier.
2208    ///
2209    /// ## Example
2210    /// ```ts
2211    /// class Foo {
2212    ///   x: number;         // false
2213    ///   declare y: string; // true
2214    /// }
2215    ///
2216    /// declare class Bar {
2217    ///   x: number;         // false
2218    /// }
2219    /// ```
2220    #[ts]
2221    pub declare: bool,
2222    #[ts]
2223    pub r#override: bool,
2224    /// `true` when created with an optional modifier (`?`)
2225    #[ts]
2226    pub optional: bool,
2227    #[ts]
2228    pub definite: bool,
2229    /// `true` when declared with a `readonly` modifier
2230    #[ts]
2231    pub readonly: bool,
2232    /// Accessibility modifier.
2233    ///
2234    /// Only ever [`Some`] for TypeScript files.
2235    ///
2236    /// ## Example
2237    ///
2238    /// ```ts
2239    /// class Foo {
2240    ///   public w: number;     // Some(TSAccessibility::Public)
2241    ///   private x: string;    // Some(TSAccessibility::Private)
2242    ///   protected y: boolean; // Some(TSAccessibility::Protected)
2243    ///   readonly z;           // None
2244    /// }
2245    /// ```
2246    #[ts]
2247    pub accessibility: Option<TSAccessibility>,
2248}
2249
2250#[ast]
2251#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2252#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
2253#[estree(no_rename_variants)]
2254pub enum PropertyDefinitionType {
2255    PropertyDefinition = 0,
2256    TSAbstractPropertyDefinition = 1,
2257}
2258
2259#[ast]
2260#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2261#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
2262pub enum MethodDefinitionKind {
2263    /// Class constructor
2264    Constructor = 0,
2265    /// Static or instance method
2266    Method = 1,
2267    /// Getter method
2268    Get = 2,
2269    /// Setter method
2270    Set = 3,
2271}
2272
2273/// An identifier for a private class member.
2274///
2275/// See: [MDN - Private class fields](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/Private_class_fields)
2276#[ast(visit)]
2277#[derive(Debug, Clone)]
2278#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2279pub struct PrivateIdentifier<'a> {
2280    pub span: Span,
2281    pub name: Atom<'a>,
2282}
2283
2284/// Class Static Block
2285///
2286/// See: [MDN - Static initialization blocks](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Classes/Static_initialization_blocks)
2287///
2288/// ## Example
2289///
2290/// ```ts
2291/// class Foo {
2292///     static {
2293///         this.someStaticProperty = 5;
2294///     }
2295/// }
2296/// ```
2297#[ast(visit)]
2298#[scope(flags = ScopeFlags::ClassStaticBlock)]
2299#[derive(Debug)]
2300#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2301pub struct StaticBlock<'a> {
2302    pub span: Span,
2303    pub body: Vec<'a, Statement<'a>>,
2304    pub scope_id: Cell<Option<ScopeId>>,
2305}
2306
2307/// ES6 Module Declaration
2308///
2309/// An ESM import or export statement.
2310///
2311/// ## Example
2312///
2313/// ```ts
2314/// // ImportDeclaration
2315/// import { foo } from 'foo';
2316/// import bar from 'bar';
2317/// import * as baz from 'baz';
2318///
2319/// // Not a ModuleDeclaration
2320/// export const a = 5;
2321///
2322/// const b = 6;
2323///
2324/// export { b };             // ExportNamedDeclaration
2325/// export default b;         // ExportDefaultDeclaration
2326/// export * as c from './c'; // ExportAllDeclaration
2327/// export = b;               // TSExportAssignment
2328/// export as namespace d;    // TSNamespaceExportDeclaration
2329/// ```
2330#[ast(visit)]
2331#[derive(Debug)]
2332#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
2333pub enum ModuleDeclaration<'a> {
2334    /// `import hello from './world.js';`
2335    /// `import * as t from './world.js';`
2336    ImportDeclaration(Box<'a, ImportDeclaration<'a>>) = 64,
2337    /// `export * as numbers from '../numbers.js'`
2338    ExportAllDeclaration(Box<'a, ExportAllDeclaration<'a>>) = 65,
2339    /// `export default 5;`
2340    ExportDefaultDeclaration(Box<'a, ExportDefaultDeclaration<'a>>) = 66,
2341    /// `export {five} from './numbers.js';`
2342    /// `export {six, seven};`
2343    ExportNamedDeclaration(Box<'a, ExportNamedDeclaration<'a>>) = 67,
2344
2345    /// `export = 5;`
2346    TSExportAssignment(Box<'a, TSExportAssignment<'a>>) = 68,
2347    /// `export as namespace React;`
2348    TSNamespaceExportDeclaration(Box<'a, TSNamespaceExportDeclaration<'a>>) = 69,
2349}
2350
2351/// Macro for matching `ModuleDeclaration`'s variants.
2352#[macro_export]
2353macro_rules! match_module_declaration {
2354    ($ty:ident) => {
2355        $ty::ImportDeclaration(_)
2356            | $ty::ExportAllDeclaration(_)
2357            | $ty::ExportDefaultDeclaration(_)
2358            | $ty::ExportNamedDeclaration(_)
2359            | $ty::TSExportAssignment(_)
2360            | $ty::TSNamespaceExportDeclaration(_)
2361    };
2362}
2363pub use match_module_declaration;
2364
2365#[ast]
2366#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2367#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
2368#[estree(no_rename_variants)]
2369pub enum AccessorPropertyType {
2370    AccessorProperty = 0,
2371    TSAbstractAccessorProperty = 1,
2372}
2373
2374/// Class Accessor Property
2375///
2376/// ## Example
2377/// ```ts
2378/// class Foo {
2379///   accessor y: string
2380/// }
2381/// ```
2382#[ast(visit)]
2383#[derive(Debug)]
2384#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2385#[estree(add_fields(declare = TsFalse, optional = TsFalse, readonly = TsFalse))]
2386pub struct AccessorProperty<'a> {
2387    pub span: Span,
2388    pub r#type: AccessorPropertyType,
2389    /// Decorators applied to the accessor property.
2390    ///
2391    /// See [`Decorator`] for more information.
2392    pub decorators: Vec<'a, Decorator<'a>>,
2393    /// The expression used to declare the property.
2394    pub key: PropertyKey<'a>,
2395    /// Type annotation on the property.
2396    ///
2397    /// Will only ever be [`Some`] for TypeScript files.
2398    #[ts]
2399    pub type_annotation: Option<Box<'a, TSTypeAnnotation<'a>>>,
2400    /// Initialized value in the declaration, if present.
2401    pub value: Option<Expression<'a>>,
2402    /// Property was declared with a computed key
2403    pub computed: bool,
2404    /// Property was declared with a `static` modifier
2405    pub r#static: bool,
2406    /// Property was declared with a `override` modifier
2407    #[ts]
2408    pub r#override: bool,
2409    /// Property has a `!` after its key.
2410    #[ts]
2411    pub definite: bool,
2412    /// Accessibility modifier.
2413    ///
2414    /// Only ever [`Some`] for TypeScript files.
2415    ///
2416    /// ## Example
2417    ///
2418    /// ```ts
2419    /// class Foo {
2420    ///   public accessor w: number     // Some(TSAccessibility::Public)
2421    ///   private accessor x: string    // Some(TSAccessibility::Private)
2422    ///   protected accessor y: boolean // Some(TSAccessibility::Protected)
2423    ///   accessor z           // None
2424    /// }
2425    /// ```
2426    #[ts]
2427    pub accessibility: Option<TSAccessibility>,
2428}
2429
2430#[ast(visit)]
2431#[derive(Debug)]
2432#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2433pub struct ImportExpression<'a> {
2434    pub span: Span,
2435    pub source: Expression<'a>,
2436    pub options: Option<Expression<'a>>,
2437    pub phase: Option<ImportPhase>,
2438}
2439
2440#[ast(visit)]
2441#[derive(Debug)]
2442#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2443pub struct ImportDeclaration<'a> {
2444    pub span: Span,
2445    /// `None` for `import 'foo'`, `Some([])` for `import {} from 'foo'`
2446    #[estree(via = ImportDeclarationSpecifiers)]
2447    pub specifiers: Option<Vec<'a, ImportDeclarationSpecifier<'a>>>,
2448    pub source: StringLiteral<'a>,
2449    pub phase: Option<ImportPhase>,
2450    /// Some(vec![]) for empty assertion
2451    #[estree(rename = "attributes", via = ImportDeclarationWithClause)]
2452    pub with_clause: Option<Box<'a, WithClause<'a>>>,
2453    /// `import type { foo } from 'bar'`
2454    #[ts]
2455    pub import_kind: ImportOrExportKind,
2456}
2457
2458/// Import Phase
2459///
2460/// <https://github.com/tc39/proposal-defer-import-eval>
2461/// <https://github.com/tc39/proposal-source-phase-imports>
2462/// <https://github.com/estree/estree/blob/2b48e56efc223ea477a45b5e034039934c5791fa/stage3/source-phase-imports.md>
2463#[ast]
2464#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2465#[generate_derive(CloneIn, Dummy, ContentEq, ESTree)]
2466pub enum ImportPhase {
2467    Source = 0,
2468    Defer = 1,
2469}
2470
2471#[ast(visit)]
2472#[derive(Debug)]
2473#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
2474pub enum ImportDeclarationSpecifier<'a> {
2475    /// `import {imported} from "source";`
2476    /// `import {imported as local} from "source";`
2477    ImportSpecifier(Box<'a, ImportSpecifier<'a>>) = 0,
2478    /// `import local from "source";`
2479    ImportDefaultSpecifier(Box<'a, ImportDefaultSpecifier<'a>>) = 1,
2480    /// `import * as local from "source";`
2481    ImportNamespaceSpecifier(Box<'a, ImportNamespaceSpecifier<'a>>) = 2,
2482}
2483
2484/// Import specifier.
2485///
2486/// ```ts
2487/// import { imported, imported2 } from "source";
2488/// //       ^^^^^^^^  ^^^^^^^^^
2489/// import { imported as local } from "source";
2490/// //       ^^^^^^^^^^^^^^^^^
2491/// import { type Foo } from "source";
2492/// //       ^^^^^^^^
2493/// ```
2494///
2495/// In the case of `import { foo }`, `imported` and `local` both are the same name,
2496/// and have the same `Span`.
2497#[ast(visit)]
2498#[derive(Debug)]
2499#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2500pub struct ImportSpecifier<'a> {
2501    pub span: Span,
2502    /// Imported symbol.
2503    /// Can only be `IdentifierName` or `StringLiteral`.
2504    pub imported: ModuleExportName<'a>,
2505    /// Binding for local symbol.
2506    pub local: BindingIdentifier<'a>,
2507    /// Value or type.
2508    /// `import { foo }`      -> `ImportOrExportKind::Value`
2509    /// `import { type Bar }` -> `ImportOrExportKind::Type`
2510    #[ts]
2511    pub import_kind: ImportOrExportKind,
2512}
2513
2514/// Default Import Specifier
2515///
2516/// ## Example
2517/// ```ts
2518/// import local from "source";
2519/// ```
2520///
2521#[ast(visit)]
2522#[derive(Debug)]
2523#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2524pub struct ImportDefaultSpecifier<'a> {
2525    pub span: Span,
2526    /// The name of the imported symbol.
2527    pub local: BindingIdentifier<'a>,
2528}
2529
2530/// Namespace import specifier
2531///
2532/// ## Example
2533/// ```ts
2534/// import * as local from "source";
2535/// ```
2536#[ast(visit)]
2537#[derive(Debug)]
2538#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2539pub struct ImportNamespaceSpecifier<'a> {
2540    pub span: Span,
2541    pub local: BindingIdentifier<'a>,
2542}
2543
2544#[ast(visit)]
2545#[derive(Debug)]
2546#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2547#[estree(no_type, no_ts_def)]
2548pub struct WithClause<'a> {
2549    #[estree(skip)]
2550    pub span: Span,
2551    #[estree(skip)]
2552    pub keyword: WithClauseKeyword,
2553    #[estree(rename = "attributes")]
2554    pub with_entries: Vec<'a, ImportAttribute<'a>>,
2555}
2556
2557#[ast]
2558#[derive(Debug, Clone, Copy, PartialEq, Eq)]
2559#[generate_derive(CloneIn, Dummy, ContentEq)]
2560#[estree(no_ts_def)]
2561pub enum WithClauseKeyword {
2562    With = 0,
2563    Assert = 1,
2564}
2565
2566#[ast(visit)]
2567#[derive(Debug)]
2568#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2569pub struct ImportAttribute<'a> {
2570    pub span: Span,
2571    pub key: ImportAttributeKey<'a>,
2572    pub value: StringLiteral<'a>,
2573}
2574
2575#[ast(visit)]
2576#[derive(Debug)]
2577#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2578pub enum ImportAttributeKey<'a> {
2579    Identifier(IdentifierName<'a>) = 0,
2580    StringLiteral(StringLiteral<'a>) = 1,
2581}
2582
2583/// Named Export Declaration
2584///
2585/// ## Example
2586///
2587/// ```ts
2588/// //       ________ specifiers
2589/// export { Foo, Bar };
2590/// export type { Baz } from 'baz';
2591/// //     ^^^^              ^^^^^
2592/// // export_kind           source
2593/// ```
2594#[ast(visit)]
2595#[derive(Debug)]
2596#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2597pub struct ExportNamedDeclaration<'a> {
2598    pub span: Span,
2599    pub declaration: Option<Declaration<'a>>,
2600    pub specifiers: Vec<'a, ExportSpecifier<'a>>,
2601    pub source: Option<StringLiteral<'a>>,
2602    /// `export type { foo }`
2603    #[ts]
2604    pub export_kind: ImportOrExportKind,
2605    /// Some(vec![]) for empty assertion
2606    #[estree(rename = "attributes", via = ExportNamedDeclarationWithClause)]
2607    pub with_clause: Option<Box<'a, WithClause<'a>>>,
2608}
2609
2610/// Export Default Declaration
2611///
2612/// ## Example
2613///
2614/// ```ts
2615/// export default HoistableDeclaration
2616/// export default ClassDeclaration
2617/// export default AssignmentExpression
2618/// ```
2619#[ast(visit)]
2620#[derive(Debug)]
2621#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2622#[estree(add_fields(exportKind = TsValue))]
2623pub struct ExportDefaultDeclaration<'a> {
2624    pub span: Span,
2625    pub declaration: ExportDefaultDeclarationKind<'a>,
2626}
2627
2628/// Export All Declaration
2629///
2630/// ## Example
2631///
2632/// ```ts
2633/// //          _______ exported
2634/// export * as numbers from '../numbers.js';
2635/// //                       ^^^^^^^^^^^^^^^ source
2636/// ```
2637#[ast(visit)]
2638#[derive(Debug)]
2639#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2640pub struct ExportAllDeclaration<'a> {
2641    pub span: Span,
2642    /// If this declaration is re-named
2643    pub exported: Option<ModuleExportName<'a>>,
2644    pub source: StringLiteral<'a>,
2645    /// Will be `Some(vec![])` for empty assertion
2646    #[estree(rename = "attributes", via = ExportAllDeclarationWithClause)]
2647    pub with_clause: Option<Box<'a, WithClause<'a>>>, // Some(vec![]) for empty assertion
2648    #[ts]
2649    pub export_kind: ImportOrExportKind, // `export type *`
2650}
2651
2652/// Export Specifier
2653///
2654/// Each [`ExportSpecifier`] is one of the named exports in an [`ExportNamedDeclaration`].
2655///
2656/// Note: `export_kind` relates to whether this specific `ExportSpecifier` is preceded by `type` keyword.
2657/// If the whole `ExportNamedDeclaration` has a `type` prefix, its `ExportSpecifier`s will still have
2658/// `export_kind: ImportOrExportKind::Value`. e.g. in this case: `export type { Foo, Bar }`.
2659///
2660/// ## Example
2661///
2662/// ```ts
2663/// //       ____ export_kind
2664/// export { type Foo as Bar };
2665/// //      local ^^^    ^^^ exported
2666/// ```
2667#[ast(visit)]
2668#[derive(Debug)]
2669#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2670pub struct ExportSpecifier<'a> {
2671    pub span: Span,
2672    pub local: ModuleExportName<'a>,
2673    pub exported: ModuleExportName<'a>,
2674    #[ts]
2675    pub export_kind: ImportOrExportKind, // `export { type Foo as Bar };`
2676}
2677
2678inherit_variants! {
2679/// Export Default Declaration Kind
2680///
2681/// Inherits variants from [`Expression`]. See [`ast` module docs] for explanation of inheritance.
2682///
2683/// [`ast` module docs]: `super`
2684#[ast(visit)]
2685#[derive(Debug)]
2686#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, GetAddress, ContentEq, ESTree)]
2687pub enum ExportDefaultDeclarationKind<'a> {
2688    #[visit(args(flags = ScopeFlags::Function))]
2689    FunctionDeclaration(Box<'a, Function<'a>>) = 64,
2690    ClassDeclaration(Box<'a, Class<'a>>) = 65,
2691
2692    TSInterfaceDeclaration(Box<'a, TSInterfaceDeclaration<'a>>) = 66,
2693
2694    // `Expression` variants added here by `inherit_variants!` macro
2695    @inherit Expression
2696}
2697}
2698
2699/// Module Export Name
2700///
2701/// Supports:
2702///   * `import {"\0 any unicode" as foo} from ""`
2703///   * `export {foo as "\0 any unicode"}`
2704/// * es2022: <https://github.com/estree/estree/blob/e6015c4c63118634749001b1cd1c3f7a0388f16e/es2022.md#modules>
2705/// * <https://github.com/tc39/ecma262/pull/2154>
2706#[ast(visit)]
2707#[derive(Debug, Clone)]
2708#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2709pub enum ModuleExportName<'a> {
2710    IdentifierName(IdentifierName<'a>) = 0,
2711    /// For `local` in `ExportSpecifier`: `foo` in `export { foo }`
2712    IdentifierReference(IdentifierReference<'a>) = 1,
2713    StringLiteral(StringLiteral<'a>) = 2,
2714}
2715
2716/// Intrinsics in Google's V8 engine, like `%GetOptimizationStatus`.
2717/// See: [runtime.h](https://github.com/v8/v8/blob/5fe0aa3bc79c0a9d3ad546b79211f07105f09585/src/runtime/runtime.h#L43)
2718#[ast(visit)]
2719#[derive(Debug)]
2720#[generate_derive(CloneIn, Dummy, TakeIn, GetSpan, GetSpanMut, ContentEq, ESTree)]
2721pub struct V8IntrinsicExpression<'a> {
2722    pub span: Span,
2723    pub name: IdentifierName<'a>,
2724    pub arguments: Vec<'a, Argument<'a>>,
2725}