mf_expression/
expression.rs1use crate::compiler::Opcode;
2use crate::vm::VM;
3use crate::{IsolateError, Variable};
4use std::marker::PhantomData;
5use std::sync::Arc;
6
7#[derive(Debug, Clone)]
8pub struct Standard;
9
10#[derive(Debug, Clone)]
11pub struct Unary;
12
13#[derive(Debug, Clone)]
14pub enum ExpressionKind {
15 Standard,
16 Unary,
17}
18
19#[derive(Debug, Clone)]
21pub struct Expression<Kind> {
22 bytecode: Arc<Vec<Opcode>>,
23 _marker: PhantomData<Kind>,
24}
25
26impl<Kind> Expression<Kind> {
27 pub fn bytecode(&self) -> &Arc<Vec<Opcode>> {
28 &self.bytecode
29 }
30}
31
32impl Expression<Standard> {
33 pub fn new_standard(bytecode: Arc<Vec<Opcode>>) -> Self {
34 Expression { bytecode, _marker: PhantomData }
35 }
36
37 pub fn kind(&self) -> ExpressionKind {
38 ExpressionKind::Standard
39 }
40
41 pub fn evaluate(
42 &self,
43 context: Variable,
44 ) -> Result<Variable, IsolateError> {
45 let mut vm = VM::new();
46 self.evaluate_with(context, &mut vm)
47 }
48
49 pub fn evaluate_with(
50 &self,
51 context: Variable,
52 vm: &mut VM,
53 ) -> Result<Variable, IsolateError> {
54 let output = vm.run(self.bytecode.as_slice(), context)?;
55 Ok(output)
56 }
57}
58
59impl Expression<Unary> {
60 pub fn new_unary(bytecode: Arc<Vec<Opcode>>) -> Self {
61 Expression { bytecode, _marker: PhantomData }
62 }
63
64 pub fn kind(&self) -> ExpressionKind {
65 ExpressionKind::Unary
66 }
67
68 pub fn evaluate(
69 &self,
70 context: Variable,
71 ) -> Result<bool, IsolateError> {
72 let mut vm = VM::new();
73 self.evaluate_with(context, &mut vm)
74 }
75
76 pub fn evaluate_with(
77 &self,
78 context: Variable,
79 vm: &mut VM,
80 ) -> Result<bool, IsolateError> {
81 let Some(context_object_ref) = context.as_object() else {
82 return Err(IsolateError::MissingContextReference);
83 };
84
85 let context_object = context_object_ref.borrow();
86 if !context_object.contains_key("$") {
87 return Err(IsolateError::MissingContextReference);
88 }
89
90 let output = vm
91 .run(self.bytecode.as_slice(), context)?
92 .as_bool()
93 .ok_or_else(|| IsolateError::ValueCastError)?;
94 Ok(output)
95 }
96}