1use crate::Span;
5use crate::ast::{Identifier, ItemExtras, Literal, SingleType, Statement, StringLiteral};
6use std::num::ParseIntError;
7
8#[derive(Debug, PartialEq)]
10pub struct Operator {
11 pub span: Span,
13 pub operation: OperatorType,
15}
16
17#[derive(Debug, PartialEq)]
19#[allow(missing_docs)]
20pub enum OperatorType {
21 Add,
22 Subtract,
23 Multiply,
24 Divide,
25 Union,
26 Intersect,
27 PowerXor,
28 GreaterThan,
29 LessThan,
30 GreaterEqual,
31 LessEqual,
32 Equal,
33 Near,
34 NotEqual,
35 And,
36 Or,
37 Xor,
38}
39
40impl OperatorType {
41 pub fn as_str(&self) -> &'static str {
43 match self {
44 Self::Add => "+",
45 Self::Subtract => "-",
46 Self::Multiply => "*",
47 Self::Divide => "/",
48 Self::Union => "|",
49 Self::Intersect => "&",
50 Self::PowerXor => "^",
51 Self::GreaterThan => ">",
52 Self::LessThan => "<",
53 Self::GreaterEqual => "≥",
54 Self::LessEqual => "≤",
55 Self::Equal => "==",
56 Self::Near => "~",
57 Self::NotEqual => "!=",
58 Self::And => "&",
59 Self::Or => "|",
60 Self::Xor => "^",
61 }
62 }
63}
64
65#[derive(Debug, PartialEq)]
67pub struct UnaryOperator {
68 pub span: Span,
70 pub operation: UnaryOperatorType,
72}
73
74#[derive(Debug, PartialEq)]
76#[allow(missing_docs)]
77pub enum UnaryOperatorType {
78 Minus,
79 Plus,
80 Not,
81}
82
83impl UnaryOperatorType {
84 pub fn as_str(&self) -> &'static str {
86 match self {
87 UnaryOperatorType::Minus => "-",
88 UnaryOperatorType::Plus => "+",
89 UnaryOperatorType::Not => "!",
90 }
91 }
92}
93
94#[derive(Debug, PartialEq)]
96#[allow(missing_docs)]
97pub enum Expression {
98 Literal(Literal),
99 Tuple(TupleExpression),
100 ArrayRange(ArrayRangeExpression),
101 ArrayList(ArrayListExpression),
102 String(FormatString),
103 QualifiedName(QualifiedName),
104 Marker(Identifier),
105 BinaryOperation(BinaryOperation),
106 UnaryOperation(UnaryOperation),
107 Block(StatementList),
108 Call(Call),
109 ElementAccess(ElementAccess),
110 If(If),
111 Error(Span),
112}
113
114impl Expression {
115 pub fn span(&self) -> Span {
117 match self {
118 Expression::Literal(ex) => ex.span(),
119 Expression::Tuple(ex) => ex.span.clone(),
120 Expression::ArrayRange(ex) => ex.span.clone(),
121 Expression::ArrayList(ex) => ex.span.clone(),
122 Expression::String(ex) => ex.span.clone(),
123 Expression::QualifiedName(ex) => ex.span.clone(),
124 Expression::Marker(ex) => ex.span.clone(),
125 Expression::BinaryOperation(ex) => ex.span.clone(),
126 Expression::UnaryOperation(ex) => ex.span.clone(),
127 Expression::Block(ex) => ex.span.clone(),
128 Expression::Call(ex) => ex.span.clone(),
129 Expression::ElementAccess(ex) => ex.span.clone(),
130 Expression::If(ex) => ex.span.clone(),
131 Expression::Error(span) => span.clone(),
132 }
133 }
134}
135
136#[derive(Debug, PartialEq)]
138#[allow(missing_docs)]
139pub struct FormatString {
140 pub span: Span,
141 pub extras: ItemExtras,
142 pub parts: Vec<StringPart>,
143}
144
145#[derive(Debug, PartialEq)]
147#[allow(missing_docs)]
148pub enum StringPart {
149 Char(StringCharacter),
150 Content(StringLiteral),
151 Expression(StringExpression),
152}
153
154#[derive(Debug, PartialEq)]
156#[allow(missing_docs)]
157pub struct StringCharacter {
158 pub span: Span,
159 pub character: char,
160}
161
162#[derive(Debug, PartialEq)]
164#[allow(missing_docs)]
165pub struct StringExpression {
166 pub span: Span,
167 pub extras: ItemExtras,
168 pub expression: Box<Expression>,
169 pub specification: Box<StringFormatSpecification>,
170}
171
172#[derive(Debug, PartialEq)]
176#[allow(missing_docs)]
177pub struct StringFormatSpecification {
178 pub span: Span,
179 pub precision: Option<Result<u32, (ParseIntError, Span)>>,
180 pub width: Option<Result<u32, (ParseIntError, Span)>>,
181}
182
183impl StringFormatSpecification {
184 pub fn is_some(&self) -> bool {
186 self.precision.is_some() || self.width.is_some()
187 }
188}
189
190#[derive(Debug, PartialEq)]
192#[allow(missing_docs)]
193pub struct TupleItem {
194 pub span: Span,
195 pub extras: ItemExtras,
196 pub name: Option<Identifier>,
197 pub value: Expression,
198}
199
200impl TupleItem {
201 pub(crate) fn dummy(span: Span) -> Self {
202 TupleItem {
203 span: span.clone(),
204 extras: ItemExtras::default(),
205 name: None,
206 value: Expression::Error(span),
207 }
208 }
209}
210
211#[derive(Debug, PartialEq)]
213#[allow(missing_docs)]
214pub struct TupleExpression {
215 pub span: Span,
216 pub extras: ItemExtras,
217 pub values: Vec<TupleItem>,
218}
219
220#[derive(Debug, PartialEq)]
222#[allow(missing_docs)]
223pub struct ArrayRangeExpression {
224 pub span: Span,
225 pub extras: ItemExtras,
226 pub start: Box<ArrayItem>,
227 pub end: Box<ArrayItem>,
228 pub ty: Option<SingleType>,
229}
230
231#[derive(Debug, PartialEq)]
233#[allow(missing_docs)]
234pub struct ArrayListExpression {
235 pub span: Span,
236 pub extras: ItemExtras,
237 pub items: Vec<ArrayItem>,
238 pub ty: Option<SingleType>,
239}
240
241#[derive(Debug, PartialEq)]
243#[allow(missing_docs)]
244pub struct ArrayItem {
245 pub span: Span,
246 pub extras: ItemExtras,
247 pub expression: Expression,
248}
249
250#[derive(Debug, PartialEq)]
252#[allow(missing_docs)]
253pub struct QualifiedName {
254 pub span: Span,
255 pub extras: ItemExtras,
256 pub parts: Vec<Identifier>,
257}
258
259#[derive(Debug, PartialEq)]
261#[allow(missing_docs)]
262pub struct BinaryOperation {
263 pub span: Span,
264 pub lhs: Box<Expression>,
265 pub operation: Operator,
266 pub rhs: Box<Expression>,
267}
268
269#[derive(Debug, PartialEq)]
271#[allow(missing_docs)]
272pub struct UnaryOperation {
273 pub span: Span,
274 pub extras: ItemExtras,
275 pub operation: UnaryOperator,
276 pub rhs: Box<Expression>,
277}
278
279#[derive(Debug, PartialEq)]
281#[allow(missing_docs)]
282pub struct Call {
283 pub span: Span,
284 pub extras: ItemExtras,
285 pub name: QualifiedName,
286 pub arguments: ArgumentList,
287}
288
289#[derive(Debug, PartialEq)]
293#[allow(missing_docs)]
294pub struct ElementAccess {
295 pub span: Span,
296 pub value: Box<Expression>,
297 pub element: Element,
298}
299
300#[derive(Debug, PartialEq)]
302#[allow(missing_docs)]
303pub enum Element {
304 Attribute(Identifier),
305 Tuple(Identifier),
306 Method(Call),
307 ArrayElement(Box<Expression>),
308}
309
310#[derive(Debug, PartialEq)]
312#[allow(missing_docs)]
313pub struct If {
314 pub span: Span,
315 pub if_span: Span,
316 pub extras: ItemExtras,
317 pub condition: Box<Expression>,
318 pub body: StatementList,
319 pub next_if_span: Option<Span>,
320 pub next_if: Option<Box<If>>,
321 pub else_span: Option<Span>,
322 pub else_body: Option<StatementList>,
323}
324
325#[derive(Debug, PartialEq)]
327#[allow(missing_docs)]
328pub struct StatementList {
329 pub span: Span,
330 pub extras: ItemExtras,
331 pub statements: Vec<Statement>,
332 pub tail: Option<Box<Statement>>,
333}
334
335impl StatementList {
336 pub(crate) fn dummy(span: Span) -> Self {
337 StatementList {
338 span,
339 extras: ItemExtras::default(),
340 statements: Vec::default(),
341 tail: None,
342 }
343 }
344}
345
346#[derive(Debug, PartialEq)]
348#[allow(missing_docs)]
349pub struct ArgumentList {
350 pub span: Span,
351 pub extras: ItemExtras,
352 pub arguments: Vec<Argument>,
353}
354
355impl ArgumentList {
356 pub(crate) fn dummy(span: Span) -> Self {
357 ArgumentList {
358 span,
359 extras: ItemExtras::default(),
360 arguments: Vec::new(),
361 }
362 }
363}
364
365#[derive(Debug, PartialEq)]
367#[allow(missing_docs)]
368pub enum Argument {
369 Unnamed(UnnamedArgument),
370 Named(NamedArgument),
371}
372
373impl Argument {
374 pub fn name(&self) -> Option<&Identifier> {
376 match self {
377 Argument::Unnamed(_) => None,
378 Argument::Named(arg) => Some(&arg.name),
379 }
380 }
381
382 pub fn value(&self) -> &Expression {
384 match self {
385 Argument::Unnamed(arg) => &arg.value,
386 Argument::Named(arg) => &arg.value,
387 }
388 }
389
390 pub fn span(&self) -> &Span {
392 match self {
393 Argument::Unnamed(arg) => &arg.span,
394 Argument::Named(arg) => &arg.span,
395 }
396 }
397}
398
399#[derive(Debug, PartialEq)]
401#[allow(missing_docs)]
402pub struct UnnamedArgument {
403 pub span: Span,
404 pub extras: ItemExtras,
405 pub value: Expression,
406}
407
408#[derive(Debug, PartialEq)]
410#[allow(missing_docs)]
411pub struct NamedArgument {
412 pub span: Span,
413 pub extras: ItemExtras,
414 pub name: Identifier,
415 pub value: Expression,
416}