use crate::Span;
use serde::{Deserialize, Serialize};
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct Program {
pub statements: Vec<Stmt>,
pub result: Expr,
pub span: Span,
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct Block {
pub statements: Vec<Stmt>,
pub result: Box<Expr>,
pub span: Span,
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct Stmt {
pub kind: StmtKind,
pub span: Span,
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub enum StmtKind {
Binding {
name: String,
value: Expr,
},
Skip {
condition: Option<Expr>,
},
}
impl Stmt {
pub fn binding(&self) -> Option<(&String, &Expr)> {
match &self.kind {
StmtKind::Binding { name, value } => Some((name, value)),
StmtKind::Skip { .. } => None,
}
}
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub struct Expr {
pub kind: ExprKind,
pub span: Span,
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub enum ObjectKey {
Static(String),
Computed(Expr),
}
impl ObjectKey {
pub fn expr(&self) -> Option<&Expr> {
match self {
ObjectKey::Static(_) => None,
ObjectKey::Computed(e) => Some(e),
}
}
}
#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)]
pub enum ExprKind {
Null,
Boolean(bool),
Integer(String),
Number(String),
String(String),
Name(String),
List(Vec<Expr>),
Object(Vec<(ObjectKey, Expr)>),
Member {
target: Box<Expr>,
field: String,
},
Index {
target: Box<Expr>,
index: Box<Expr>,
},
Call {
callee: Box<Expr>,
arguments: Vec<Expr>,
},
Unary {
op: UnaryOp,
value: Box<Expr>,
},
Binary {
op: BinaryOp,
left: Box<Expr>,
right: Box<Expr>,
},
Conditional {
then_expr: Box<Expr>,
condition: Box<Expr>,
else_expr: Box<Expr>,
},
If {
condition: Box<Expr>,
then_block: Block,
else_block: Option<Block>,
},
For {
binding: String,
collection: Box<Expr>,
limit: Option<u32>,
body: Block,
},
Fold {
accumulator: String,
init: Box<Expr>,
binding: String,
collection: Box<Expr>,
body: Block,
},
Fail {
arguments: Vec<Expr>,
},
Boundary {
retries: u32,
body: Block,
error_binding: String,
catch: Block,
},
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
pub enum UnaryOp {
Negate,
Not,
}
#[derive(Debug, Clone, Copy, PartialEq, Eq, Serialize, Deserialize)]
pub enum BinaryOp {
Add,
Subtract,
Multiply,
Divide,
Remainder,
Equal,
NotEqual,
Less,
LessEqual,
Greater,
GreaterEqual,
In,
And,
Or,
}