use crate::command::Command; use crate::commands::{OUTPUT, PARSE_TREE, PRINT_JSON, PRINT_YAML, RULES}; use crate::rules::Result; use crate::utils::reader::Reader; use crate::utils::writer::Writer; use clap::{Arg, ArgAction, ArgMatches, ValueHint}; use std::fs::File; #[derive(Clone, Copy, Eq, PartialEq)] pub struct ParseTree {} #[allow(clippy::new_without_default)] impl ParseTree { pub fn new() -> Self { ParseTree {} } } impl Command for ParseTree { fn name(&self) -> &'static str { PARSE_TREE } fn command(&self) -> clap::Command { clap::Command::new(PARSE_TREE) .about("Prints out the parse tree for the rules defined in the file.") .arg( Arg::new(RULES.0) .long(RULES.0) .short(RULES.1) .help("Provide a rules file") .value_hint(ValueHint::FilePath) .required(false), ) .arg( Arg::new(OUTPUT.0) .long(OUTPUT.0) .short(OUTPUT.1) .help("Write to output file") .value_hint(ValueHint::FilePath) .required(false), ) .arg( Arg::new(PRINT_JSON.0) .long(PRINT_JSON.0) .short(PRINT_JSON.1) .action(ArgAction::SetTrue) .help("Print output in JSON format. Use -p as the short flag"), ) .arg( Arg::new(PRINT_YAML.0) .long(PRINT_YAML.0) .short(PRINT_YAML.1) .action(ArgAction::SetTrue) .required(false) .help("Print output in YAML format"), ) .arg_required_else_help(true) } fn execute(&self, app: &ArgMatches, writer: &mut Writer, reader: &mut Reader) -> Result { let mut file: Box = match app.get_one::(RULES.0) { Some(file) => Box::new(std::io::BufReader::new(File::open(file)?)), None => Box::new(reader), }; let mut content = String::new(); file.read_to_string(&mut content)?; let span = crate::rules::parser::Span::new_extra(&content, ""); let rules = crate::rules::parser::rules_file(span)?; match app.get_flag(PRINT_JSON.0) { true => serde_json::to_writer_pretty(writer, &rules)?, false => serde_yaml::to_writer(writer, &rules)?, } Ok(0_i32) } }