use ast_nodes::{Directed, Undirected};
use lex::PeekableLexer;
use parse::{Constructable, ParseOR};
pub mod ast_nodes;
mod lex;
mod parse;
pub enum DotGraph {
Undirected(Box<ast_nodes::Graph<Undirected>>),
Directed(Box<ast_nodes::Graph<Directed>>),
}
impl std::str::FromStr for DotGraph {
type Err = anyhow::Error;
fn from_str(s: &str) -> Result<Self, Self::Err> {
let peekable_lexer = PeekableLexer::from(s);
let dir_or_undir =
ParseOR::<ast_nodes::Graph<Directed>, ast_nodes::Graph<Undirected>>::from_lexer(
peekable_lexer,
)?
.0;
match dir_or_undir {
ParseOR {
t_val: None,
v_val: Some(undirect),
} => Ok(Self::Undirected(Box::new(undirect))),
ParseOR {
t_val: Some(direct),
v_val: None,
} => Ok(Self::Directed(Box::new(direct))),
_ => Err(anyhow::anyhow!(
"Error; couldn't parse as either directed or undirected graph"
)),
}
}
}
#[cfg(test)]
mod tests {
use super::DotGraph;
use std::str::FromStr;
#[test]
fn lib_api_sanity_test() {
let test_str = "graph G { A -> { B, D} }";
let _ = DotGraph::from_str(test_str).unwrap();
}
}