1use bigdecimal::BigDecimal;
2
3pub type Program<'a> = (Vec<Statement>, pest::Span<'a>);
5
6pub trait ASTNodeSpan {
8 fn span(&self) -> Span;
9 fn span_mut(&mut self) -> &mut Span;
10}
11
12#[derive(Debug, Clone, Copy, PartialEq, Eq)]
14pub struct Span {
15 pub start: usize,
17 pub end: usize,
19}
20
21impl Span {
22 pub fn new(start: usize, end: usize) -> Self {
24 Self { start, end }
25 }
26}
27
28impl From<pest::Span<'_>> for Span {
29 fn from(span: pest::Span<'_>) -> Self {
30 Self::new(span.start(), span.end())
31 }
32}
33
34impl PartialEq<pest::Span<'_>> for Span {
35 fn eq(&self, other: &pest::Span<'_>) -> bool {
36 self.start == other.start() && self.end == other.end()
37 }
38}
39
40#[derive(Debug, Clone, PartialEq, Eq)]
42pub struct Ident {
43 pub ident: String,
45 pub span: Span,
47}
48
49#[derive(Debug, Clone, PartialEq, Eq)]
51pub struct Arg {
52 pub expr: ExpressionStatement,
54 pub is_unpack: bool,
56 pub span: Span,
58}
59
60#[derive(Debug, Clone, PartialEq, Eq)]
62pub struct Param {
63 pub ident: Ident,
65 pub is_pack: bool,
67}
68
69#[derive(Debug, Clone, PartialEq, Eq)]
71pub enum Visibility {
72 Public,
74 Private,
76}
77
78#[derive(Debug, Clone, PartialEq, Eq)]
81pub struct Block {
82 pub statements: Vec<Statement>,
84 pub span: Span,
86}
87
88#[derive(Debug, Clone, PartialEq, Eq)]
90pub enum Statement {
91 Function(FunctionStatement),
93 Assignment(AssignmentStatement),
95 Return(ReturnStatement),
97 Expression(ExpressionStatement),
99}
100
101#[derive(Debug, Clone, PartialEq, Eq)]
103pub enum ExpressionStatement {
104 FunctionCall(FunctionCallExpression),
106 Value(ValueExpression),
108}
109
110#[derive(Debug, Clone, PartialEq, Eq)]
112pub struct FunctionStatement {
113 pub ident: Option<Ident>,
115 pub params: Vec<Param>,
117 pub block: Option<Block>,
120 pub visibility: Visibility,
122 pub span: Span,
124}
125
126#[derive(Debug, Clone, PartialEq, Eq)]
130pub struct AssignmentStatement {
131 pub ident: Ident,
133 pub expression: ExpressionStatement,
135 pub span: Span,
137}
138
139#[derive(Debug, Clone, PartialEq, Eq)]
141pub struct ReturnStatement {
142 pub span: Span,
144 pub value: ExpressionStatement,
146}
147
148#[derive(Debug, Clone, PartialEq, Eq)]
150pub struct FunctionCallExpression {
151 pub callable: ValueExpression,
153 pub args: Vec<Arg>,
155 pub span: Span,
157}
158
159#[derive(Debug, Clone, PartialEq, Eq)]
161pub enum ValueExpression {
162 Ident(Ident),
164 Object(ObjectExpression),
166}
167
168#[derive(Debug, Clone, PartialEq, Eq)]
170pub enum ObjectExpression {
171 Function(FunctionStatement),
173 String(String, Span),
175 Int(BigDecimal, Span),
177 Float(BigDecimal, Span),
179 Bool(bool, Span),
181 Array(Vec<ExpressionStatement>, Span),
183 Nil(Span),
185}
186
187impl ObjectExpression {
188 pub fn type_name(&self) -> &'static str {
190 match self {
191 ObjectExpression::Function(_) => "function",
192 ObjectExpression::String(_, _) => "string",
193 ObjectExpression::Int(_, _) => "int",
194 ObjectExpression::Float(_, _) => "float",
195 ObjectExpression::Bool(_, _) => "bool",
196 ObjectExpression::Array(_, _) => "array",
197 ObjectExpression::Nil(_) => "nil",
198 }
199 }
200}
201
202impl ToString for ObjectExpression {
203 fn to_string(&self) -> String {
204 match self {
205 ObjectExpression::Function(func) => {
206 let func_type = if func.block.is_none() {
207 "<builtin-function> "
208 } else {
209 ""
210 };
211 format!(
212 "{}{}{}",
213 func_type,
214 func.ident
215 .as_ref()
216 .map_or_else(|| "Anonymous Function".to_string(), |i| i.ident.clone()),
217 func.params
218 .iter()
219 .map(|param| format!("<{}>", param.ident.ident))
220 .collect::<String>()
221 )
222 }
223 ObjectExpression::String(string, _) => string.clone(),
224 ObjectExpression::Int(int, _) => int.to_string(),
225 ObjectExpression::Float(float, _) => float.to_string(),
226 ObjectExpression::Bool(boolean, _) => boolean.to_string(),
227 ObjectExpression::Array(arr, _) => {
228 format!(
229 "[{}]",
230 arr.iter()
231 .map(|e| match e {
232 ExpressionStatement::Value(ValueExpression::Object(obj)) => {
233 obj.to_string()
234 }
235 _ => unreachable!("array can only contain objects"),
236 })
237 .collect::<Vec<_>>()
238 .join(", ")
239 )
240 }
241 ObjectExpression::Nil(_) => "nil".to_string(),
242 }
243 }
244}
245
246impl ASTNodeSpan for Ident {
247 fn span(&self) -> Span {
248 self.span
249 }
250 fn span_mut(&mut self) -> &mut Span {
251 &mut self.span
252 }
253}
254
255impl ASTNodeSpan for Param {
256 fn span(&self) -> Span {
257 self.ident.span()
258 }
259 fn span_mut(&mut self) -> &mut Span {
260 self.ident.span_mut()
261 }
262}
263
264impl ASTNodeSpan for Block {
265 fn span(&self) -> Span {
266 self.span
267 }
268 fn span_mut(&mut self) -> &mut Span {
269 &mut self.span
270 }
271}
272
273impl ASTNodeSpan for FunctionStatement {
274 fn span(&self) -> Span {
275 self.span
276 }
277 fn span_mut(&mut self) -> &mut Span {
278 &mut self.span
279 }
280}
281
282impl ASTNodeSpan for AssignmentStatement {
283 fn span(&self) -> Span {
284 self.span
285 }
286 fn span_mut(&mut self) -> &mut Span {
287 &mut self.span
288 }
289}
290
291impl ASTNodeSpan for ReturnStatement {
292 fn span(&self) -> Span {
293 self.span
294 }
295 fn span_mut(&mut self) -> &mut Span {
296 &mut self.span
297 }
298}
299
300impl ASTNodeSpan for FunctionCallExpression {
301 fn span(&self) -> Span {
302 self.span
303 }
304 fn span_mut(&mut self) -> &mut Span {
305 &mut self.span
306 }
307}
308
309impl ASTNodeSpan for ValueExpression {
310 fn span(&self) -> Span {
311 match self {
312 ValueExpression::Ident(ident) => ident.span(),
313 ValueExpression::Object(object) => object.span(),
314 }
315 }
316 fn span_mut(&mut self) -> &mut Span {
317 match self {
318 ValueExpression::Ident(ident) => ident.span_mut(),
319 ValueExpression::Object(object) => object.span_mut(),
320 }
321 }
322}
323
324impl ASTNodeSpan for ObjectExpression {
325 fn span(&self) -> Span {
326 match self {
327 ObjectExpression::Function(function) => function.span(),
328 ObjectExpression::String(_, span) => *span,
329 ObjectExpression::Int(_, span) => *span,
330 ObjectExpression::Float(_, span) => *span,
331 ObjectExpression::Bool(_, span) => *span,
332 ObjectExpression::Array(_, span) => *span,
333 ObjectExpression::Nil(span) => *span,
334 }
335 }
336 fn span_mut(&mut self) -> &mut Span {
337 match self {
338 ObjectExpression::Function(function) => function.span_mut(),
339 ObjectExpression::String(_, span) => span,
340 ObjectExpression::Int(_, span) => span,
341 ObjectExpression::Float(_, span) => span,
342 ObjectExpression::Bool(_, span) => span,
343 ObjectExpression::Array(_, span) => span,
344 ObjectExpression::Nil(span) => span,
345 }
346 }
347}
348
349impl ASTNodeSpan for ExpressionStatement {
350 fn span(&self) -> Span {
351 match self {
352 ExpressionStatement::FunctionCall(function_call) => function_call.span(),
353 ExpressionStatement::Value(value) => value.span(),
354 }
355 }
356 fn span_mut(&mut self) -> &mut Span {
357 match self {
358 ExpressionStatement::FunctionCall(function_call) => function_call.span_mut(),
359 ExpressionStatement::Value(value) => value.span_mut(),
360 }
361 }
362}
363
364impl ASTNodeSpan for Statement {
365 fn span(&self) -> Span {
366 match self {
367 Statement::Function(function) => function.span(),
368 Statement::Assignment(assignment) => assignment.span(),
369 Statement::Return(return_statement) => return_statement.span(),
370 Statement::Expression(expression) => expression.span(),
371 }
372 }
373 fn span_mut(&mut self) -> &mut Span {
374 match self {
375 Statement::Function(function) => function.span_mut(),
376 Statement::Assignment(assignment) => assignment.span_mut(),
377 Statement::Return(return_statement) => return_statement.span_mut(),
378 Statement::Expression(expression) => expression.span_mut(),
379 }
380 }
381}