Skip to main content

zapcode_core/parser/
ir.rs

1use serde::{Deserialize, Serialize};
2
3/// Result type for parsing a class body: (constructor, instance methods, static methods).
4pub type ClassBodyParts = (Option<Box<FunctionDef>>, Vec<ClassMethod>, Vec<ClassMethod>);
5
6/// Span information for error reporting.
7#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
8pub struct Span {
9    pub start: u32,
10    pub end: u32,
11}
12
13impl std::fmt::Display for Span {
14    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
15        write!(f, "{}..{}", self.start, self.end)
16    }
17}
18
19impl From<oxc_span::Span> for Span {
20    fn from(s: oxc_span::Span) -> Self {
21        Span {
22            start: s.start,
23            end: s.end,
24        }
25    }
26}
27
28/// A complete program — a list of statements.
29#[derive(Debug, Clone, Serialize, Deserialize)]
30pub struct Program {
31    pub body: Vec<Statement>,
32    pub functions: Vec<FunctionDef>,
33}
34
35/// Function definition stored separately (hoisted).
36#[derive(Debug, Clone, Serialize, Deserialize)]
37pub struct FunctionDef {
38    pub name: Option<String>,
39    pub params: Vec<ParamPattern>,
40    pub body: Vec<Statement>,
41    pub is_async: bool,
42    pub is_generator: bool,
43    pub is_arrow: bool,
44    pub span: Span,
45}
46
47/// Parameter pattern (simple name or destructuring).
48#[derive(Debug, Clone, Serialize, Deserialize)]
49pub enum ParamPattern {
50    Ident(String),
51    ObjectDestructure(Vec<DestructureField>),
52    ArrayDestructure(Vec<Option<ParamPattern>>),
53    Rest(String),
54    DefaultValue {
55        pattern: Box<ParamPattern>,
56        default: Expr,
57    },
58}
59
60#[derive(Debug, Clone, Serialize, Deserialize)]
61pub struct DestructureField {
62    pub key: String,
63    pub alias: Option<String>,
64    pub default: Option<Expr>,
65}
66
67#[derive(Debug, Clone, Serialize, Deserialize)]
68pub enum Statement {
69    VariableDecl {
70        kind: VarKind,
71        declarations: Vec<VarDeclarator>,
72        span: Span,
73    },
74    Expression {
75        expr: Expr,
76        span: Span,
77    },
78    Return {
79        value: Option<Expr>,
80        span: Span,
81    },
82    If {
83        test: Expr,
84        consequent: Vec<Statement>,
85        alternate: Option<Vec<Statement>>,
86        span: Span,
87    },
88    While {
89        test: Expr,
90        body: Vec<Statement>,
91        span: Span,
92    },
93    ForOf {
94        binding: ForBinding,
95        iterable: Expr,
96        body: Vec<Statement>,
97        span: Span,
98    },
99    For {
100        init: Option<Box<Statement>>,
101        test: Option<Expr>,
102        update: Option<Expr>,
103        body: Vec<Statement>,
104        span: Span,
105    },
106    Block {
107        body: Vec<Statement>,
108        span: Span,
109    },
110    Throw {
111        value: Expr,
112        span: Span,
113    },
114    TryCatch {
115        try_body: Vec<Statement>,
116        catch_param: Option<String>,
117        catch_body: Vec<Statement>,
118        finally_body: Option<Vec<Statement>>,
119        span: Span,
120    },
121    Break {
122        span: Span,
123    },
124    Continue {
125        span: Span,
126    },
127    FunctionDecl {
128        func_index: usize,
129        span: Span,
130    },
131    Switch {
132        discriminant: Expr,
133        cases: Vec<SwitchCase>,
134        span: Span,
135    },
136    DoWhile {
137        body: Vec<Statement>,
138        test: Expr,
139        span: Span,
140    },
141    ClassDecl {
142        name: String,
143        super_class: Option<String>,
144        constructor: Option<Box<FunctionDef>>,
145        methods: Vec<ClassMethod>,
146        static_methods: Vec<ClassMethod>,
147        span: Span,
148    },
149}
150
151#[derive(Debug, Clone, Serialize, Deserialize)]
152pub struct ClassMethod {
153    pub name: String,
154    pub func: FunctionDef,
155}
156
157#[derive(Debug, Clone, Serialize, Deserialize)]
158pub struct SwitchCase {
159    pub test: Option<Expr>,
160    pub consequent: Vec<Statement>,
161}
162
163#[derive(Debug, Clone, Serialize, Deserialize)]
164pub enum ForBinding {
165    Ident(String),
166    Destructure(ParamPattern),
167}
168
169#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
170pub enum VarKind {
171    Const,
172    Let,
173    Var,
174}
175
176#[derive(Debug, Clone, Serialize, Deserialize)]
177pub struct VarDeclarator {
178    pub pattern: AssignTarget,
179    pub init: Option<Expr>,
180}
181
182#[derive(Debug, Clone, Serialize, Deserialize)]
183pub enum AssignTarget {
184    Ident(String),
185    ObjectDestructure(Vec<DestructureField>),
186    ArrayDestructure(Vec<Option<AssignTarget>>),
187}
188
189#[derive(Debug, Clone, Serialize, Deserialize)]
190pub enum Expr {
191    // Literals
192    NumberLit(f64),
193    StringLit(String),
194    BoolLit(bool),
195    NullLit,
196    UndefinedLit,
197    TemplateLit {
198        quasis: Vec<String>,
199        exprs: Vec<Expr>,
200    },
201    RegExpLit {
202        pattern: String,
203        flags: String,
204    },
205
206    // Identifiers
207    Ident(String),
208
209    // Compound
210    Array(Vec<Option<Expr>>),
211    Object(Vec<ObjProperty>),
212    Spread(Box<Expr>),
213
214    // Operations
215    Binary {
216        op: BinOp,
217        left: Box<Expr>,
218        right: Box<Expr>,
219    },
220    Unary {
221        op: UnaryOp,
222        operand: Box<Expr>,
223    },
224    Update {
225        op: UpdateOp,
226        prefix: bool,
227        operand: Box<Expr>,
228    },
229    Logical {
230        op: LogicalOp,
231        left: Box<Expr>,
232        right: Box<Expr>,
233    },
234    Conditional {
235        test: Box<Expr>,
236        consequent: Box<Expr>,
237        alternate: Box<Expr>,
238    },
239    Assignment {
240        op: AssignOp,
241        target: Box<Expr>,
242        value: Box<Expr>,
243    },
244    Sequence(Vec<Expr>),
245
246    // Access
247    Member {
248        object: Box<Expr>,
249        property: String,
250        optional: bool,
251    },
252    ComputedMember {
253        object: Box<Expr>,
254        property: Box<Expr>,
255        optional: bool,
256    },
257
258    // Calls
259    Call {
260        callee: Box<Expr>,
261        args: Vec<Expr>,
262        optional: bool,
263    },
264    New {
265        callee: Box<Expr>,
266        args: Vec<Expr>,
267    },
268
269    // Functions
270    ArrowFunction {
271        func_index: usize,
272    },
273    FunctionExpr {
274        func_index: usize,
275    },
276
277    // Async
278    Await(Box<Expr>),
279
280    // Generators
281    Yield {
282        value: Option<Box<Expr>>,
283        delegate: bool,
284    },
285
286    // Typeof
287    TypeOf(Box<Expr>),
288
289    // Classes
290    ClassExpr {
291        name: Option<String>,
292        super_class: Option<String>,
293        constructor: Option<Box<FunctionDef>>,
294        methods: Vec<ClassMethod>,
295        static_methods: Vec<ClassMethod>,
296    },
297}
298
299#[derive(Debug, Clone, Serialize, Deserialize)]
300pub struct ObjProperty {
301    pub kind: PropKind,
302    pub key: String,
303    pub value: Expr,
304    pub computed: bool,
305}
306
307#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
308pub enum PropKind {
309    Init,
310    Get,
311    Set,
312    Method,
313    Shorthand,
314    Spread,
315}
316
317#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
318pub enum BinOp {
319    Add,
320    Sub,
321    Mul,
322    Div,
323    Rem,
324    Pow,
325    Eq,
326    Neq,
327    StrictEq,
328    StrictNeq,
329    Lt,
330    Lte,
331    Gt,
332    Gte,
333    BitAnd,
334    BitOr,
335    BitXor,
336    Shl,
337    Shr,
338    Ushr,
339    In,
340    InstanceOf,
341}
342
343#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
344pub enum UnaryOp {
345    Neg,
346    Not,
347    BitNot,
348    Void,
349}
350
351#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
352pub enum UpdateOp {
353    Increment,
354    Decrement,
355}
356
357#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
358pub enum LogicalOp {
359    And,
360    Or,
361    NullishCoalescing,
362}
363
364#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
365pub enum AssignOp {
366    Assign,
367    AddAssign,
368    SubAssign,
369    MulAssign,
370    DivAssign,
371    RemAssign,
372    PowAssign,
373    BitAndAssign,
374    BitOrAssign,
375    BitXorAssign,
376    ShlAssign,
377    ShrAssign,
378    UshrAssign,
379    NullishAssign,
380    AndAssign,
381    OrAssign,
382}