static_graph/parser/
ident.rs

1use faststr::FastStr;
2use nom::{
3    bytes::complete::take_while,
4    character::complete::{char, satisfy},
5    combinator::{map, recognize},
6    multi::many0,
7    sequence::tuple,
8    IResult,
9};
10
11use std::ops::Deref;
12
13use super::Parser;
14
15#[derive(Debug, Clone)]
16pub struct Ident(pub FastStr);
17
18impl Deref for Ident {
19    type Target = FastStr;
20
21    fn deref(&self) -> &Self::Target {
22        &self.0
23    }
24}
25
26impl<'a> Parser<'a> for Ident {
27    fn parse(input: &'a str) -> IResult<&'a str, Ident> {
28        map(
29            recognize(tuple((
30                many0(char('_')),
31                satisfy(|c| c.is_ascii_alphabetic()),
32                take_while(|c: char| c.is_ascii_alphanumeric() || c == '_'),
33            ))),
34            |ident: &str| -> Ident { Ident(FastStr::new(ident)) },
35        )(input)
36    }
37}
38
39#[cfg(test)]
40mod tests {
41    use super::*;
42
43    #[test]
44    fn test_ident() {
45        let input = "_Foo";
46        match super::Ident::parse(input) {
47            Ok((remain, ident)) => {
48                assert_eq!(remain, "");
49                assert_eq!(ident.0, "_Foo");
50            }
51            Err(e) => panic!("Error: {e:?}"),
52        }
53    }
54}