Skip to content

Commit

Permalink
Merge pull request #349 from CohenArthur/multi-types
Browse files Browse the repository at this point in the history
Allow multi type parsing
  • Loading branch information
CohenArthur authored Nov 30, 2021
2 parents 0b28031 + d207120 commit 892d1d1
Show file tree
Hide file tree
Showing 2 changed files with 44 additions and 2 deletions.
42 changes: 40 additions & 2 deletions src/parser/constructs.rs
Original file line number Diff line number Diff line change
Expand Up @@ -426,15 +426,33 @@ fn typed_args(input: &str) -> ParseResult<&str, Vec<DecArg>> {
Ok((input, args))
}

// FIXME: This should not return a String
fn multi_type(input: &str) -> ParseResult<&str, String> {
// FIXME: Remove with #342
fn whitespace_plus_id(input: &str) -> ParseResult<&str, String> {
delimited(nom_next, Token::identifier, nom_next)(input)
}

// FIXME: We want to allow generic types here later on
let (input, first_type) = whitespace_plus_id(input)?;

let (input, mut types) = many0(preceded(Token::pipe, whitespace_plus_id))(input)?;

// FIXME: Remove clone once we have a proper MultiType struct to return
types.insert(0, first_type.clone());

Ok((input, first_type))
}

/// typed_arg = spaced_identifier ':' spaced_identifier
fn typed_arg(input: &str) -> ParseResult<&str, DecArg> {
let (input, id) = spaced_identifier(input)?;
let (input, _) = Token::colon(input)?;
let input = next(input);
let (input, ty) = Token::identifier(input)?;
let (input, types) = multi_type(input)?;
let input = next(input);

Ok((input, DecArg::new(id, TypeId::new(ty))))
Ok((input, DecArg::new(id, TypeId::new(types))))
}

/// type_inst_arg = spaced_identifier ':' expr
Expand Down Expand Up @@ -1150,4 +1168,24 @@ func void() { }"##;

assert_eq!(input, "");
}

#[test]
fn multi_type_2() {
assert!(expr("func takes_mt(a: int | string) {}").is_ok())
}

#[test]
fn multi_type_unclosed() {
assert!(expr("func invalid_mt(a: int |) {}").is_err())
}

#[test]
fn multi_type_long() {
assert!(expr("func long_mt(a: int | string | float | char | bool) {}").is_ok())
}

#[test]
fn multi_type_in_type_dec() {
assert!(expr("type MultiTy(a: int | string | float | char | bool);").is_ok())
}
}
4 changes: 4 additions & 0 deletions src/parser/tokens.rs
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,10 @@ impl Token {
Token::specific_char(input, ',')
}

pub fn pipe(input: &str) -> ParseResult<&str, char> {
Token::specific_char(input, '|')
}

pub fn left_curly_bracket(input: &str) -> ParseResult<&str, char> {
Token::specific_char(input, '{')
}
Expand Down

0 comments on commit 892d1d1

Please sign in to comment.