package types import "fmt" // Node represents a node in the abstract syntax tree type Node interface { String() string } // Statement represents any statement type Statement interface { Node statementNode() } // Expression represents any expression type Expression interface { Node expressionNode() } // --- Expressions --- // LiteralExpr represents a literal value type LiteralExpr struct { Value any } func (l LiteralExpr) expressionNode() {} func (l LiteralExpr) String() string { return fmt.Sprintf("%v", l.Value) } // BinaryExpr represents a binary operation type BinaryExpr struct { Left Expression Operator Token Right Expression } func (b BinaryExpr) expressionNode() {} func (b BinaryExpr) String() string { return fmt.Sprintf("(%s %s %s)", b.Left.String(), b.Operator.Lexeme, b.Right.String()) } // VariableExpr represents a variable reference type VariableExpr struct { Name Token } func (v VariableExpr) expressionNode() {} func (v VariableExpr) String() string { return v.Name.Lexeme } // CallExpr represents a function call type CallExpr struct { Callee Expression Paren Token Arguments []Expression } func (c CallExpr) expressionNode() {} func (c CallExpr) String() string { args := "" for i, arg := range c.Arguments { if i > 0 { args += ", " } args += arg.String() } return fmt.Sprintf("%s(%s)", c.Callee.String(), args) } // --- Statements --- // ExpressionStmt represents an expression statement type ExpressionStmt struct { Expression Expression } func (e ExpressionStmt) statementNode() {} func (e ExpressionStmt) String() string { return e.Expression.String() } // AssignStmt represents a variable assignment type AssignStmt struct { Name Token Value Expression } func (a AssignStmt) statementNode() {} func (a AssignStmt) String() string { return fmt.Sprintf("%s = %s", a.Name.Lexeme, a.Value.String()) } // FunctionStmt represents a function declaration type FunctionStmt struct { Name Token Params []Token IsVariadic bool Body []Statement } func (f FunctionStmt) statementNode() {} func (f FunctionStmt) String() string { params := "" for i, param := range f.Params { if i > 0 { params += ", " } params += param.Lexeme } if f.IsVariadic { if len(f.Params) > 0 { params += ", ..." } else { params += "..." } } return fmt.Sprintf("fn %s(%s) ... end", f.Name.Lexeme, params) } // FunctionStmt represents a function expression (anonymous function) type FunctionExpr struct { Params []Token IsVariadic bool Body []Statement } func (f FunctionExpr) expressionNode() {} func (f FunctionExpr) String() string { params := "" for i, param := range f.Params { if i > 0 { params += ", " } params += param.Lexeme } if f.IsVariadic { if len(f.Params) > 0 { params += ", ..." } else { params += "..." } } return fmt.Sprintf("fn(%s) ... end", params) } // ReturnStmt represents a return statement type ReturnStmt struct { Keyword Token Value Expression } func (r ReturnStmt) statementNode() {} func (r ReturnStmt) String() string { if r.Value == nil { return "return" } return fmt.Sprintf("return %s", r.Value.String()) } // IfStmt represents an if statement type IfStmt struct { Condition Expression ThenBranch []Statement ElseIfs []struct { Condition Expression Body []Statement } ElseBranch []Statement } func (i IfStmt) statementNode() {} func (i IfStmt) String() string { return "if ... then ... end" } // EchoStmt represents an echo statement type EchoStmt struct { Keyword Token Value Expression } func (e EchoStmt) statementNode() {} func (e EchoStmt) String() string { return fmt.Sprintf("echo %s", e.Value.String()) } // UnaryExpr represents a unary operation type UnaryExpr struct { Operator Token Right Expression } func (u UnaryExpr) expressionNode() {} func (u UnaryExpr) String() string { return fmt.Sprintf("(%s%s)", u.Operator.Lexeme, u.Right.String()) } // BlockStmt represents a block of statements type BlockStmt struct { Statements []Statement } func (b BlockStmt) statementNode() {} func (b BlockStmt) String() string { return "{ ... }" }