devalang_core/core/parser/handler/
condition.rs1use crate::core::{
2 lexer::token::TokenKind,
3 parser::{
4 driver::parser::Parser,
5 statement::{Statement, StatementKind},
6 },
7 store::global::GlobalStore,
8};
9use devalang_types::Value;
10use std::collections::HashMap;
11
12pub fn parse_condition_token(parser: &mut Parser, global_store: &mut GlobalStore) -> Statement {
13 parser.advance(); let Some(if_token) = parser.previous_clone() else {
15 return Statement::unknown();
16 };
17
18 let Some(condition) = parser.parse_condition_until_colon() else {
19 return crate::core::parser::statement::error_from_token(
20 if_token,
21 "Expected condition after 'if'".to_string(),
22 );
23 };
24
25 parser.advance_if(TokenKind::Colon);
26 let base_indent = if_token.indent;
27
28 let if_body = parser.parse_block_until_else_or_dedent(base_indent, global_store);
29
30 let mut root_map = HashMap::new();
31 root_map.insert("condition".to_string(), condition);
32 root_map.insert("body".to_string(), Value::Block(if_body));
33
34 let mut current = &mut root_map;
35
36 while let Some(tok) = parser.peek_clone() {
38 if tok.lexeme != "else" || tok.indent != base_indent {
40 break;
41 }
42
43 parser.advance(); let next_condition = if parser.peek_is("if") {
47 parser.advance(); let Some(cond) = parser.parse_condition_until_colon() else {
49 return crate::core::parser::statement::error_from_token(
50 tok.clone(),
51 "Expected condition after 'else if'".to_string(),
52 );
53 };
54 parser.advance_if(TokenKind::Colon);
55 Some(cond)
56 } else {
57 parser.advance_if(TokenKind::Colon);
58 None
59 };
60
61 let body = parser.parse_block_until_else_or_dedent(base_indent, global_store);
62
63 let mut next_map = HashMap::new();
64 if let Some(cond) = next_condition {
65 next_map.insert("condition".to_string(), cond);
66 }
67 next_map.insert("body".to_string(), Value::Block(body));
68
69 current.insert("next".to_string(), Value::Map(next_map));
70 current = match current.get_mut("next") {
71 Some(Value::Map(map)) => map,
72 _ => break,
73 };
74 }
75
76 Statement {
77 kind: StatementKind::If,
78 value: Value::Map(root_map),
79 indent: if_token.indent,
80 line: if_token.line,
81 column: if_token.column,
82 }
83}