Make alternative clause parser more flexible.

The spirit here is to make it easier to discover this syntax. People
  have different intuition about it and the single pipe may not be the
  most obvious one.

  It is however the recommended syntax, and the formatter will rewrite
  any of the other to it.
This commit is contained in:
KtorZ 2024-08-06 11:31:11 +02:00
parent 8c121f6d97
commit 1ae6640cd0
No known key found for this signature in database
GPG Key ID: 33173CB6F77F4277
3 changed files with 206 additions and 1 deletions

View File

@ -11,7 +11,17 @@ pub fn parser(
expression: Recursive<'_, Token, UntypedExpr, ParseError>,
) -> impl Parser<Token, ast::UntypedClause, Error = ParseError> + '_ {
pattern()
.then(just(Token::Vbar).ignore_then(pattern()).repeated().or_not())
.then(
choice((
just(Token::Vbar),
just(Token::VbarVbar),
just(Token::Or),
just(Token::Comma),
))
.ignore_then(pattern())
.repeated()
.or_not(),
)
.then(choice((just(Token::If)
.ignore_then(guard())
.or_not()
@ -76,4 +86,18 @@ mod tests {
"#
);
}
#[test]
fn when_clause_alternative() {
assert_expr!(
r#"
when val is {
Bar1{..} | Bar2{..} -> todo
Bar3{..} || Bar4{..} -> todo
Bar5{..} or Bar6{..} -> todo
Bar5{..}, Bar6{..} -> todo
}
"#
);
}
}

View File

@ -0,0 +1,177 @@
---
source: crates/aiken-lang/src/parser/expr/when/clause.rs
description: "Code:\n\nwhen val is {\n Bar1{..} | Bar2{..} -> todo\n Bar3{..} || Bar4{..} -> todo\n Bar5{..} or Bar6{..} -> todo\n Bar5{..}, Bar6{..} -> todo\n}\n"
---
When {
location: 0..136,
subject: Var {
location: 5..8,
name: "val",
},
clauses: [
UntypedClause {
location: 16..43,
patterns: [
Constructor {
is_record: true,
location: 16..24,
name: "Bar1",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
21..23,
),
tipo: (),
},
Constructor {
is_record: true,
location: 27..35,
name: "Bar2",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
32..34,
),
tipo: (),
},
],
then: Trace {
kind: Todo,
location: 39..43,
then: ErrorTerm {
location: 39..43,
},
label: String {
location: 39..43,
value: "aiken::todo",
},
arguments: [],
},
},
UntypedClause {
location: 46..74,
patterns: [
Constructor {
is_record: true,
location: 46..54,
name: "Bar3",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
51..53,
),
tipo: (),
},
Constructor {
is_record: true,
location: 58..66,
name: "Bar4",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
63..65,
),
tipo: (),
},
],
then: Trace {
kind: Todo,
location: 70..74,
then: ErrorTerm {
location: 70..74,
},
label: String {
location: 70..74,
value: "aiken::todo",
},
arguments: [],
},
},
UntypedClause {
location: 77..105,
patterns: [
Constructor {
is_record: true,
location: 77..85,
name: "Bar5",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
82..84,
),
tipo: (),
},
Constructor {
is_record: true,
location: 89..97,
name: "Bar6",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
94..96,
),
tipo: (),
},
],
then: Trace {
kind: Todo,
location: 101..105,
then: ErrorTerm {
location: 101..105,
},
label: String {
location: 101..105,
value: "aiken::todo",
},
arguments: [],
},
},
UntypedClause {
location: 108..134,
patterns: [
Constructor {
is_record: true,
location: 108..116,
name: "Bar5",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
113..115,
),
tipo: (),
},
Constructor {
is_record: true,
location: 118..126,
name: "Bar6",
arguments: [],
module: None,
constructor: (),
spread_location: Some(
123..125,
),
tipo: (),
},
],
then: Trace {
kind: Todo,
location: 130..134,
then: ErrorTerm {
location: 130..134,
},
label: String {
location: 130..134,
value: "aiken::todo",
},
arguments: [],
},
},
],
}

View File

@ -812,6 +812,10 @@ where
&mut self.data_types,
)?;
if name == "foo" {
println!("{:#?}", checked_module.ast);
}
if our_modules.contains(checked_module.name.as_str()) {
self.warnings.extend(warnings);
}