1use std::vec;
2
3use regex::Regex;
4
5use crate::{
6 function_call::get_fn_obj,
7 syntax_tree::{SyntaxTree, TreeType, TreeValueType},
8 token::{Token, TokenType},
9 EngineArg, EngineArgType,
10};
11
12#[derive(Debug)]
13struct FnArg {
14 layer: usize,
15 args: usize,
16}
17
18pub fn parse(tokens: Vec<Token>, inputs: &Vec<EngineArg>) -> SyntaxTree {
19 if tokens[0].type_ == TokenType::Input {
20 parse_input_exp(&tokens[0], inputs)
21 } else {
22 parse_fn_exp(tokens, inputs)
23 }
24}
25
26pub fn parse_input_exp(token: &Token, inputs: &Vec<EngineArg>) -> SyntaxTree {
27 let input_value = inputs.iter().find(|input| input.key == token.value);
28 if input_value.is_none() && inputs.len() > 0 {
29 panic!("{}", format!("Input '{}' is not informed.", token.value));
30 }
31 SyntaxTree {
32 childs: vec![],
33 node: input_value.unwrap().value.clone(),
34 tree_type: TreeType::Input,
35 tree_val_type: TreeValueType::String,
36 }
37}
38
39pub fn parse_fn_exp(tokens: Vec<Token>, inputs: &Vec<EngineArg>) -> SyntaxTree {
40 let tokens = tokens[..tokens.len() - 1].to_vec();
41 let mut tokens_iter = tokens.iter();
42 let mut tree = SyntaxTree::new(
43 tokens_iter.next().unwrap().value.clone(),
44 TreeType::FunctionCall,
45 vec![],
46 TreeValueType::String,
47 );
48
49 let mut layer = 0;
50 let mut layer_args: Vec<FnArg> = vec![FnArg { layer: 0, args: 0 }];
51
52 for token in tokens_iter.rev() {
53 if token.type_ == TokenType::Function {
54 let args = layer_args[layer].args;
55 let range = (tree.childs.len() - args)..;
56 let mut args: Vec<SyntaxTree> = tree.get_childs(range);
57 args.reverse();
58
59 let fn_obj = get_fn_obj(&token.value);
60 let fun = SyntaxTree::new(
61 token.value.clone(),
62 TreeType::FunctionCall,
63 args,
64 fn_obj.return_type(),
65 );
66
67 tree.append_child(fun);
68 layer -= 1;
69 layer_args[layer].args += 1;
70 }
71
72 if token.type_ == TokenType::Input {
73 let input_value = inputs.into_iter().find(|input| input.key == token.value);
74
75 if input_value.is_none() && inputs.len() > 0 {
76 panic!("{}", format!("Input '{}' is not informed.", token.value));
77 }
78
79 let input_value = input_value.unwrap();
80
81 let input_type = match input_value.value_type {
82 EngineArgType::String => TreeValueType::String,
83 EngineArgType::Integer => TreeValueType::Integer,
84 };
85
86 let input = SyntaxTree::new(
87 input_value.value.clone(),
88 TreeType::Input,
89 vec![],
90 input_type,
91 );
92 tree.append_child(input);
93 layer_args[layer].args += 1;
94 }
95
96 if token.type_ == TokenType::Integer {
97 let input = SyntaxTree::new(
98 token.value.clone(),
99 TreeType::Input,
100 vec![],
101 TreeValueType::Integer,
102 );
103 tree.append_child(input);
104 layer_args[layer].args += 1;
105 }
106
107 if token.type_ == TokenType::String {
108 let value = &token.value[1..token.value.len() - 1];
109 let middle_quotes_reg = Regex::new(r"\\'").unwrap();
110 let real_string_value = middle_quotes_reg.replace_all(value, "'");
111
112 let input = SyntaxTree::new(
113 real_string_value.to_string(),
114 TreeType::Input,
115 vec![],
116 TreeValueType::String,
117 );
118
119 tree.append_child(input);
120 layer_args[layer].args += 1;
121 }
122
123 if token.type_ == TokenType::BracketRight {
124 layer += 1;
125
126 if layer_args.get(layer).is_none() {
127 layer_args.push(FnArg { args: 0, layer })
128 } else {
129 layer_args[layer] = FnArg { args: 0, layer }
130 }
131 }
132 }
133
134 tree.childs.reverse();
135 tree
136}