cfn_guard/commands/
helper.rs1use enumflags2::BitFlags;
5
6use crate::commands::reporters::validate::generic_summary::GenericSummary;
7use crate::commands::validate::{DataFile, OutputFormatType, Reporter};
8use crate::rules::errors::Error;
9use crate::rules::eval::eval_rules_file;
10use crate::rules::eval_context::root_scope;
11use crate::rules::path_value::traversal::Traversal;
12use crate::rules::path_value::PathAwareValue;
13use crate::rules::Result;
14use std::convert::TryFrom;
15use std::io::BufWriter;
16use std::rc::Rc;
17
18#[allow(dead_code)]
19pub struct ValidateInput<'a> {
20 pub content: &'a str,
21 pub file_name: &'a str,
22}
23
24#[allow(dead_code)]
25pub fn validate_and_return_json(
26 data: ValidateInput,
27 rules: ValidateInput,
28 verbose: bool,
29) -> Result<String> {
30 let path_value = match serde_json::from_str::<serde_json::Value>(data.content) {
31 Ok(value) => PathAwareValue::try_from(value),
32 Err(_) => {
33 let value = serde_yaml::from_str::<serde_yaml::Value>(data.content)?;
34 PathAwareValue::try_from(value)
35 }
36 }
37 .map_err(|e| {
38 Error::ParseError(format!(
39 "Unable to process data in file {}, Error {e},",
40 data.file_name,
41 ))
42 })?;
43
44 let input_data = DataFile {
45 content: "".to_string(), path_value,
47 name: data.file_name.to_owned(),
48 };
49
50 let span = crate::rules::parser::Span::new_extra(rules.content, rules.file_name);
51
52 let rules_file_name = rules.file_name;
53 return match crate::rules::parser::rules_file(span) {
54 Ok(Some(rules)) => {
55 let mut write_output = BufWriter::new(Vec::new());
56 let root = input_data.path_value;
57 let traversal = Traversal::from(&root);
58 let mut root_scope = root_scope(&rules, Rc::new(root.clone()));
59 let status = eval_rules_file(&rules, &mut root_scope, Some(&input_data.name))?;
60 let root_record = root_scope.reset_recorder().extract();
61
62 if verbose {
63 return Ok(serde_json::to_string_pretty(&root_record)?);
64 }
65
66 let reporter = &GenericSummary::new(BitFlags::empty()) as &dyn Reporter;
67
68 reporter.report_eval(
69 &mut write_output,
70 status,
71 &root_record,
72 rules_file_name,
73 data.file_name,
74 data.content,
75 &traversal,
76 OutputFormatType::JSON,
77 )?;
78
79 match String::from_utf8(write_output.buffer().to_vec()) {
80 Ok(val) => Ok(val),
81 Err(e) => Err(Error::ParseError(e.to_string())),
82 }
83 }
84 Ok(None) => Ok(String::default()),
85 Err(e) => Err(Error::ParseError(e.to_string())),
86 };
87}