luau_parser/impl/block/
if_statement.rs1use luau_lexer::prelude::{Error, Keyword, Lexer, Token, TokenType};
8
9use crate::{
10 safe_unwrap,
11 types::{
12 Block, ElseIfStatement, ElseStatement, Expression, IfStatement, Parse, Pointer, TryParse,
13 TryParseWithArgs,
14 },
15};
16
17const END_TOKENS: [TokenType; 3] = [
19 TokenType::Keyword(Keyword::End),
20 TokenType::Keyword(Keyword::Elseif),
21 TokenType::Keyword(Keyword::Else),
22];
23
24impl Parse for IfStatement {
25 fn parse(if_keyword: Token, lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
26 if if_keyword != TokenType::Keyword(Keyword::If) {
27 return None;
28 }
29
30 let condition = safe_unwrap!(
31 lexer,
32 errors,
33 "Expected <expr>",
34 Pointer::<Expression>::try_parse(lexer, errors)
35 );
36
37 next_token_recoverable!(
38 lexer,
39 then_keyword,
40 TokenType::Keyword(Keyword::Then),
41 TokenType::Keyword(Keyword::Then),
42 errors,
43 "Expected `then`"
44 );
45
46 let body = Block::try_parse_with(lexer, errors, END_TOKENS).unwrap_or_default();
47
48 let else_if_statements =
49 Vec::<ElseIfStatement>::try_parse(lexer, errors).unwrap_or_default();
50
51 let else_statement = ElseStatement::try_parse(lexer, errors);
52 next_token_recoverable!(
53 lexer,
54 end_keyword,
55 TokenType::Keyword(Keyword::End),
56 TokenType::Keyword(Keyword::End),
57 errors,
58 "Expected `end`"
59 );
60
61 Some(Self {
62 if_keyword,
63 condition,
64 then_keyword,
65 body,
66 else_if_statements,
67 else_statement,
68 end_keyword,
69 })
70 }
71}
72impl TryParse for IfStatement {}
73
74impl Parse for ElseIfStatement {
75 fn parse(elseif_keyword: Token, lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
76 if elseif_keyword != TokenType::Keyword(Keyword::Elseif) {
77 return None;
78 }
79
80 let condition = safe_unwrap!(
81 lexer,
82 errors,
83 "Expected <expr>",
84 Pointer::<Expression>::try_parse(lexer, errors)
85 );
86
87 next_token_recoverable!(
88 lexer,
89 then_keyword,
90 TokenType::Keyword(Keyword::Then),
91 TokenType::Keyword(Keyword::Then),
92 errors,
93 "Expected `then`"
94 );
95
96 let body = Block::try_parse_with(lexer, errors, END_TOKENS).unwrap_or_default();
97
98 Some(Self {
99 elseif_keyword,
100 condition,
101 then_keyword,
102 body,
103 })
104 }
105}
106impl TryParse for ElseIfStatement {}
107
108impl Parse for ElseStatement {
109 fn parse(else_keyword: Token, lexer: &mut Lexer, errors: &mut Vec<Error>) -> Option<Self> {
110 if else_keyword != TokenType::Keyword(Keyword::Else) {
111 return None;
112 }
113
114 Some(Self {
115 else_keyword,
116 body: Block::try_parse_with(lexer, errors, TokenType::Keyword(Keyword::End))
117 .unwrap_or_default(),
118 })
119 }
120}
121impl TryParse for ElseStatement {}