Skip to content

Commit 918714f

Browse files
Add 'dec' suffix to decimal literals (#389)
## Usage and product changes Require decimal literals to be suffixed with 'dec' ## Implementation Updates grammar & datastructures.
1 parent bb23f98 commit 918714f

File tree

4 files changed

+54
-11
lines changed

4 files changed

+54
-11
lines changed

rust/parser/literal.rs

Lines changed: 21 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,8 @@ use crate::{
99
parser::{IntoChildNodes, Node, Rule, RuleMatcher},
1010
value::{
1111
BooleanLiteral, DateFragment, DateLiteral, DateTimeLiteral, DateTimeTZLiteral, DurationDate, DurationLiteral,
12-
DurationTime, IntegerLiteral, Literal, NumericLiteral, Sign, SignedDecimalLiteral, SignedIntegerLiteral,
13-
StringLiteral, TimeFragment, TimeZone, ValueLiteral,
12+
DurationTime, IntegerLiteral, Literal, NumericLiteral, Sign, SignedDecimalLiteral, SignedDoubleLiteral,
13+
SignedIntegerLiteral, StringLiteral, TimeFragment, TimeZone, ValueLiteral,
1414
},
1515
};
1616

@@ -23,6 +23,7 @@ pub(super) fn visit_value_literal(node: Node<'_>) -> Literal {
2323
Rule::boolean_literal => ValueLiteral::Boolean(BooleanLiteral { value: child.as_str().to_owned() }),
2424
Rule::signed_integer => ValueLiteral::Integer(visit_signed_integer(child)),
2525
Rule::signed_decimal => ValueLiteral::Decimal(visit_signed_decimal(child)),
26+
Rule::signed_double => ValueLiteral::Double(visit_signed_double(child)),
2627

2728
Rule::datetime_tz_literal => ValueLiteral::DateTimeTz(visit_datetime_tz_literal(child)),
2829
Rule::datetime_literal => ValueLiteral::DateTime(visit_datetime_literal(child)),
@@ -79,15 +80,29 @@ fn visit_signed_decimal(node: Node<'_>) -> SignedDecimalLiteral {
7980
debug_assert_eq!(node.as_rule(), Rule::signed_decimal);
8081
let mut children = node.into_children();
8182
let first_node = children.consume_any();
82-
let (sign, decimal) = match first_node.as_rule() {
83+
let (sign, decimal_with_suffix) = match first_node.as_rule() {
84+
Rule::sign => (Some(visit_sign(first_node)), children.consume_expected(Rule::decimal_literal).as_str()),
85+
Rule::decimal_literal => (None, first_node.as_str()),
86+
_ => unreachable!("{}", TypeQLError::IllegalGrammar { input: first_node.to_string() }),
87+
};
88+
debug_assert_eq!(children.try_consume_any(), None);
89+
let decimal = decimal_with_suffix.trim_end_matches("dec").to_owned();
90+
SignedDecimalLiteral { sign, decimal }
91+
}
92+
93+
fn visit_signed_double(node: Node<'_>) -> SignedDoubleLiteral {
94+
debug_assert_eq!(node.as_rule(), Rule::signed_double);
95+
let mut children = node.into_children();
96+
let first_node = children.consume_any();
97+
let (sign, double) = match first_node.as_rule() {
8398
Rule::sign => {
84-
(Some(visit_sign(first_node)), children.consume_expected(Rule::decimal_literal).as_str().to_owned())
99+
(Some(visit_sign(first_node)), children.consume_expected(Rule::double_literal).as_str().to_owned())
85100
}
86-
Rule::decimal_literal => (None, first_node.as_str().to_owned()),
101+
Rule::double_literal => (None, first_node.as_str().to_owned()),
87102
_ => unreachable!("{}", TypeQLError::IllegalGrammar { input: first_node.to_string() }),
88103
};
89104
debug_assert_eq!(children.try_consume_any(), None);
90-
SignedDecimalLiteral { sign, decimal }
105+
SignedDoubleLiteral { sign, double }
91106
}
92107

93108
fn visit_datetime_tz_literal(node: Node<'_>) -> DateTimeTZLiteral {

rust/parser/test/match_queries.rs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -487,3 +487,12 @@ $type relates someRole;"#;
487487
// let expected = typeql_match!(var("x").isa(cvar("type")), cvar("type").relates("someRole"));
488488
assert_valid_eq_repr!(expected, parsed, query);
489489
}
490+
491+
#[test]
492+
fn test_parsing_double_decimal_literal() {
493+
let query = r#"match
494+
let $x = -5.0 + -4.0dec;"#;
495+
let parsed = parse_query(query).unwrap();
496+
// let expected = todo!("When typeql builders exist");
497+
assert_valid_eq_repr!(expected, parsed, query);
498+
}

rust/parser/typeql.pest

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -319,10 +319,11 @@ value_type_primitive = { BOOLEAN | INTEGER | DOUBLE | DECIMAL
319319
| STRING
320320
}
321321
value_literal = { quoted_string_literal | datetime_tz_literal | datetime_literal | date_literal
322-
| duration_literal | boolean_literal | signed_decimal | signed_integer
322+
| duration_literal | boolean_literal | signed_decimal | signed_double | signed_integer
323323
}
324324

325325
signed_decimal = { sign? ~ decimal_literal }
326+
signed_double = { sign? ~ double_literal }
326327
signed_integer = { sign? ~ integer_literal }
327328
sign = { PLUS | MINUS }
328329

@@ -548,8 +549,9 @@ TRUE = @{ "true" ~ WB }
548549
FALSE = @{ "false" ~ WB }
549550

550551
integer_literal = @{ ASCII_DIGIT+ }
551-
decimal_literal = @{ ASCII_DIGIT+ ~ "." ~ ASCII_DIGIT+ ~ ( ^"e" ~ sign? ~ integer_literal )? }
552-
numeric_literal = @{ decimal_literal | integer_literal }
552+
decimal_literal = @{ ASCII_DIGIT+ ~ "." ~ ASCII_DIGIT+ ~ "dec" }
553+
double_literal = @{ ASCII_DIGIT+ ~ "." ~ ASCII_DIGIT+ ~ ( ^"e" ~ sign? ~ integer_literal )? }
554+
numeric_literal = @{ double_literal | integer_literal }
553555

554556
date_literal = ${ date_fragment ~ WB }
555557
datetime_literal = ${ date_fragment ~ "T" ~ time ~ WB }

rust/value.rs

Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ use std::fmt::{self, Formatter};
99
use crate::{
1010
common::{error::TypeQLError, Span, Spanned},
1111
pretty::Pretty,
12-
Result,
12+
token, Result,
1313
};
1414

1515
#[derive(Debug, Clone, Eq, PartialEq)]
@@ -44,6 +44,12 @@ pub struct SignedIntegerLiteral {
4444
pub integral: String,
4545
}
4646

47+
#[derive(Debug, Clone, Eq, PartialEq)]
48+
pub struct SignedDoubleLiteral {
49+
pub sign: Option<Sign>,
50+
pub double: String,
51+
}
52+
4753
#[derive(Debug, Clone, Eq, PartialEq)]
4854
pub struct SignedDecimalLiteral {
4955
pub sign: Option<Sign>,
@@ -119,6 +125,7 @@ pub enum ValueLiteral {
119125
Boolean(BooleanLiteral),
120126
Integer(SignedIntegerLiteral),
121127
Decimal(SignedDecimalLiteral),
128+
Double(SignedDoubleLiteral),
122129
Date(DateLiteral),
123130
DateTime(DateTimeLiteral),
124131
DateTimeTz(DateTimeTZLiteral),
@@ -159,6 +166,7 @@ impl fmt::Display for ValueLiteral {
159166
ValueLiteral::Boolean(value) => fmt::Display::fmt(value, f),
160167
ValueLiteral::Integer(value) => fmt::Display::fmt(value, f),
161168
ValueLiteral::Decimal(value) => fmt::Display::fmt(value, f),
169+
ValueLiteral::Double(value) => fmt::Display::fmt(value, f),
162170
ValueLiteral::Date(value) => fmt::Display::fmt(value, f),
163171
ValueLiteral::DateTime(value) => fmt::Display::fmt(value, f),
164172
ValueLiteral::DateTimeTz(value) => fmt::Display::fmt(value, f),
@@ -274,7 +282,16 @@ impl fmt::Display for SignedDecimalLiteral {
274282
if let Some(sign) = &self.sign {
275283
fmt::Display::fmt(sign, f)?;
276284
}
277-
f.write_str(self.decimal.as_str())
285+
write!(f, "{}dec", self.decimal.as_str())
286+
}
287+
}
288+
289+
impl fmt::Display for SignedDoubleLiteral {
290+
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
291+
if let Some(sign) = &self.sign {
292+
fmt::Display::fmt(sign, f)?;
293+
}
294+
f.write_str(self.double.as_str())
278295
}
279296
}
280297

0 commit comments

Comments
 (0)