ara_parser/tree/definition/
enum.rs

1use bincode::Decode;
2use bincode::Encode;
3use schemars::JsonSchema;
4use serde::Deserialize;
5use serde::Serialize;
6
7use crate::tree::comment::CommentGroup;
8use crate::tree::definition::attribute::AttributeGroupDefinition;
9use crate::tree::definition::constant::ClassishConstantDefinition;
10use crate::tree::definition::function::MethodDefinition;
11use crate::tree::expression::Expression;
12use crate::tree::identifier::Identifier;
13use crate::tree::identifier::TemplatedIdentifier;
14use crate::tree::token::Keyword;
15use crate::tree::utils::CommaSeparated;
16use crate::tree::Node;
17
18#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
19#[serde(rename_all = "snake_case", tag = "type", content = "data")]
20pub enum EnumDefinition {
21    Backed(BackedEnumDefinition),
22    Unit(UnitEnumDefinition),
23}
24
25#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
26#[serde(rename_all = "snake_case")]
27pub struct UnitEnumDefinition {
28    pub comments: CommentGroup,
29    pub attributes: Vec<AttributeGroupDefinition>,
30    pub r#enum: Keyword,
31    pub name: Identifier,
32    pub implements: Option<EnumImplementsDefinition>,
33    pub body: UnitEnumBodyDefinition,
34}
35
36#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
37#[serde(rename_all = "snake_case")]
38pub struct EnumImplementsDefinition {
39    pub implements: Keyword,
40    pub interfaces: CommaSeparated<TemplatedIdentifier>,
41}
42
43#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
44#[serde(rename_all = "snake_case")]
45pub struct UnitEnumBodyDefinition {
46    pub left_brace: usize,
47    pub members: Vec<UnitEnumMemberDefinition>,
48    pub right_brace: usize,
49}
50
51#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
52#[serde(rename_all = "snake_case", tag = "type", content = "value")]
53pub enum UnitEnumMemberDefinition {
54    Case(UnitEnumCaseDefinition),
55    Method(MethodDefinition),
56    Constant(ClassishConstantDefinition),
57}
58
59#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
60#[serde(rename_all = "snake_case")]
61pub struct UnitEnumCaseDefinition {
62    pub attributes: Vec<AttributeGroupDefinition>,
63    pub case: Keyword,
64    pub name: Identifier,
65    pub semicolon: usize,
66}
67
68#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
69#[serde(rename_all = "snake_case")]
70pub struct BackedEnumDefinition {
71    pub comments: CommentGroup,
72    pub attributes: Vec<AttributeGroupDefinition>,
73    pub r#enum: Keyword,
74    pub name: Identifier,
75    pub backed_type: BackedEnumTypeDefinition,
76    pub implements: Option<EnumImplementsDefinition>,
77    pub body: BackedEnumBodyDefinition,
78}
79
80#[derive(Debug, Clone, Hash, Eq, PartialEq, Deserialize, Serialize, Encode, Decode, JsonSchema)]
81#[serde(tag = "type", content = "value")]
82pub enum BackedEnumTypeDefinition {
83    String(usize, Identifier),
84    Int(usize, Identifier),
85}
86
87#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
88#[serde(rename_all = "snake_case")]
89pub struct BackedEnumBodyDefinition {
90    pub left_brace: usize,
91    pub members: Vec<BackedEnumMemberDefinition>,
92    pub right_brace: usize,
93}
94
95#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
96#[serde(rename_all = "snake_case", tag = "type", content = "value")]
97pub enum BackedEnumMemberDefinition {
98    Case(BackedEnumCaseDefinition),
99    Method(MethodDefinition),
100    Constant(ClassishConstantDefinition),
101}
102
103#[derive(Debug, PartialEq, Eq, Clone, Hash, Deserialize, Serialize, Encode, Decode, JsonSchema)]
104#[serde(rename_all = "snake_case")]
105pub struct BackedEnumCaseDefinition {
106    pub attributes: Vec<AttributeGroupDefinition>,
107    pub case: Keyword,
108    pub name: Identifier,
109    pub equals: usize,
110    pub value: Expression,
111    pub semicolon: usize,
112}
113
114impl Node for EnumDefinition {
115    fn comments(&self) -> Option<&CommentGroup> {
116        None
117    }
118
119    fn initial_position(&self) -> usize {
120        match &self {
121            Self::Backed(definition) => definition.initial_position(),
122            Self::Unit(definition) => definition.initial_position(),
123        }
124    }
125
126    fn final_position(&self) -> usize {
127        match &self {
128            Self::Backed(definition) => definition.final_position(),
129            Self::Unit(definition) => definition.final_position(),
130        }
131    }
132
133    fn children(&self) -> Vec<&dyn Node> {
134        match &self {
135            Self::Backed(definition) => vec![definition],
136            Self::Unit(definition) => vec![definition],
137        }
138    }
139
140    fn get_description(&self) -> String {
141        match &self {
142            Self::Backed(definition) => definition.get_description(),
143            Self::Unit(definition) => definition.get_description(),
144        }
145    }
146}
147
148impl Node for UnitEnumDefinition {
149    fn comments(&self) -> Option<&CommentGroup> {
150        Some(&self.comments)
151    }
152
153    fn initial_position(&self) -> usize {
154        if let Some(attributes) = self.attributes.first() {
155            attributes.initial_position()
156        } else {
157            self.r#enum.initial_position()
158        }
159    }
160
161    fn final_position(&self) -> usize {
162        self.body.right_brace + 1
163    }
164
165    fn children(&self) -> Vec<&dyn Node> {
166        let mut children: Vec<&dyn Node> = vec![&self.r#enum, &self.name];
167
168        for attribute in &self.attributes {
169            children.push(attribute);
170        }
171
172        if let Some(implements) = &self.implements {
173            children.push(implements);
174        }
175
176        children.push(&self.body);
177
178        children
179    }
180
181    fn get_description(&self) -> String {
182        "unit enum definition".to_string()
183    }
184}
185
186impl Node for EnumImplementsDefinition {
187    fn initial_position(&self) -> usize {
188        self.implements.initial_position()
189    }
190
191    fn final_position(&self) -> usize {
192        if let Some(last_interface) = self.interfaces.inner.last() {
193            let last_interface_position = last_interface.final_position();
194            if let Some(last_comma) = self.interfaces.commas.last() {
195                let last_comma_position = last_comma + 1;
196                if last_comma_position > last_interface_position {
197                    return last_comma_position;
198                }
199            }
200
201            return last_interface_position;
202        }
203
204        self.implements.final_position()
205    }
206
207    fn children(&self) -> Vec<&dyn Node> {
208        let mut children: Vec<&dyn Node> = vec![&self.implements];
209
210        for interface in &self.interfaces.inner {
211            children.push(interface);
212        }
213
214        children
215    }
216
217    fn get_description(&self) -> String {
218        "enum implements definition".to_string()
219    }
220}
221
222impl Node for UnitEnumBodyDefinition {
223    fn initial_position(&self) -> usize {
224        self.left_brace
225    }
226
227    fn final_position(&self) -> usize {
228        self.right_brace + 1
229    }
230
231    fn children(&self) -> Vec<&dyn Node> {
232        self.members
233            .iter()
234            .map(|member| member as &dyn Node)
235            .collect()
236    }
237
238    fn get_description(&self) -> String {
239        "unit enum body definition".to_string()
240    }
241}
242
243impl Node for UnitEnumMemberDefinition {
244    fn initial_position(&self) -> usize {
245        match &self {
246            Self::Case(case) => case.initial_position(),
247            Self::Method(method) => method.initial_position(),
248            Self::Constant(constant) => constant.initial_position(),
249        }
250    }
251
252    fn final_position(&self) -> usize {
253        match &self {
254            Self::Case(case) => case.final_position(),
255            Self::Method(method) => method.final_position(),
256            Self::Constant(constant) => constant.final_position(),
257        }
258    }
259
260    fn children(&self) -> Vec<&dyn Node> {
261        match &self {
262            Self::Case(case) => vec![case],
263            Self::Method(method) => vec![method],
264            Self::Constant(constant) => vec![constant],
265        }
266    }
267
268    fn get_description(&self) -> String {
269        match &self {
270            Self::Case(case) => case.get_description(),
271            Self::Method(method) => method.get_description(),
272            Self::Constant(constant) => constant.get_description(),
273        }
274    }
275}
276
277impl Node for UnitEnumCaseDefinition {
278    fn initial_position(&self) -> usize {
279        if let Some(attributes) = self.attributes.first() {
280            attributes.initial_position()
281        } else {
282            self.case.initial_position()
283        }
284    }
285
286    fn final_position(&self) -> usize {
287        self.semicolon + 1
288    }
289
290    fn children(&self) -> Vec<&dyn Node> {
291        let mut children: Vec<&dyn Node> = vec![&self.case];
292        for attribute in &self.attributes {
293            children.push(attribute);
294        }
295
296        children
297    }
298
299    fn get_description(&self) -> String {
300        "unit enum case definition".to_string()
301    }
302}
303
304impl Node for BackedEnumDefinition {
305    fn comments(&self) -> Option<&CommentGroup> {
306        Some(&self.comments)
307    }
308
309    fn initial_position(&self) -> usize {
310        if let Some(attributes) = self.attributes.first() {
311            attributes.initial_position()
312        } else {
313            self.r#enum.initial_position()
314        }
315    }
316
317    fn final_position(&self) -> usize {
318        self.body.right_brace + 1
319    }
320
321    fn children(&self) -> Vec<&dyn Node> {
322        let mut children: Vec<&dyn Node> = vec![&self.r#enum, &self.name, &self.backed_type];
323        for attribute in &self.attributes {
324            children.push(attribute);
325        }
326
327        if let Some(implements) = &self.implements {
328            children.push(implements);
329        }
330
331        children.push(&self.body);
332
333        children
334    }
335
336    fn get_description(&self) -> String {
337        "backed enum definition".to_string()
338    }
339}
340
341impl Node for BackedEnumTypeDefinition {
342    fn initial_position(&self) -> usize {
343        match &self {
344            Self::String(colon, _) | Self::Int(colon, _) => *colon,
345        }
346    }
347
348    fn final_position(&self) -> usize {
349        match &self {
350            Self::String(_, identifier) | Self::Int(_, identifier) => identifier.final_position(),
351        }
352    }
353
354    fn children(&self) -> Vec<&dyn Node> {
355        match &self {
356            Self::String(_, identifier) | Self::Int(_, identifier) => vec![identifier],
357        }
358    }
359
360    fn get_description(&self) -> String {
361        "backed enum type definition".to_string()
362    }
363}
364
365impl Node for BackedEnumBodyDefinition {
366    fn initial_position(&self) -> usize {
367        self.left_brace
368    }
369
370    fn final_position(&self) -> usize {
371        self.right_brace + 1
372    }
373
374    fn children(&self) -> Vec<&dyn Node> {
375        self.members
376            .iter()
377            .map(|member| member as &dyn Node)
378            .collect()
379    }
380
381    fn get_description(&self) -> String {
382        "backed enum body definition".to_string()
383    }
384}
385
386impl Node for BackedEnumMemberDefinition {
387    fn initial_position(&self) -> usize {
388        match &self {
389            Self::Case(case) => case.initial_position(),
390            Self::Method(method) => method.initial_position(),
391            Self::Constant(constant) => constant.initial_position(),
392        }
393    }
394
395    fn final_position(&self) -> usize {
396        match &self {
397            Self::Case(case) => case.final_position(),
398            Self::Method(method) => method.final_position(),
399            Self::Constant(constant) => constant.final_position(),
400        }
401    }
402
403    fn children(&self) -> Vec<&dyn Node> {
404        match &self {
405            Self::Case(case) => vec![case],
406            Self::Method(method) => vec![method],
407            Self::Constant(constant) => vec![constant],
408        }
409    }
410
411    fn get_description(&self) -> String {
412        match &self {
413            Self::Case(case) => case.get_description(),
414            Self::Method(method) => method.get_description(),
415            Self::Constant(constant) => constant.get_description(),
416        }
417    }
418}
419
420impl Node for BackedEnumCaseDefinition {
421    fn initial_position(&self) -> usize {
422        if let Some(attributes) = self.attributes.first() {
423            attributes.initial_position()
424        } else {
425            self.case.initial_position()
426        }
427    }
428
429    fn final_position(&self) -> usize {
430        self.semicolon + 1
431    }
432
433    fn children(&self) -> Vec<&dyn Node> {
434        vec![&self.case, &self.name, &self.value]
435    }
436
437    fn get_description(&self) -> String {
438        "backed enum case definition".to_string()
439    }
440}