From cf6aacc4c3d9a350fdd202c7470f38f772ea1736 Mon Sep 17 00:00:00 2001 From: Jake Howard Date: Wed, 19 Jul 2017 22:10:47 +0100 Subject: [PATCH] Type checking for config --- src/config/mod.rs | 2 ++ src/config/validate.rs | 11 ++----- src/config/validate_types.rs | 64 ++++++++++++++++++++++++++++++++++++ 3 files changed, 68 insertions(+), 9 deletions(-) create mode 100644 src/config/validate_types.rs diff --git a/src/config/mod.rs b/src/config/mod.rs index d7d778a..27e1025 100644 --- a/src/config/mod.rs +++ b/src/config/mod.rs @@ -6,6 +6,8 @@ use std::collections::HashMap; pub mod read; pub mod validate; pub mod consts; +pub mod validate_types; + #[derive(Debug, Serialize, Deserialize, Default)] pub struct Config { diff --git a/src/config/validate.rs b/src/config/validate.rs index 8b3c3e6..596e476 100644 --- a/src/config/validate.rs +++ b/src/config/validate.rs @@ -4,6 +4,7 @@ use std::vec::Vec; pub type ValidationResult = Result<(), String>; use config::read; +use config::validate_types::check_config_types; fn check_required_keys(config: &Value) -> ValidationResult { @@ -16,10 +17,6 @@ fn check_required_keys(config: &Value) -> ValidationResult { } fn check_input_files(config: &Value) -> ValidationResult { - match config.get("input").unwrap() { - &Value::Sequence(_) => (), - _ => return Err("Input must be sequence".into()), - } let files = read::get_input_files(config); for file in files.iter() { @@ -31,10 +28,6 @@ fn check_input_files(config: &Value) -> ValidationResult { } fn check_output_files(config: &Value) -> ValidationResult { - match config.get("output").unwrap() { - &Value::Mapping(_) => (), - _ => return Err("Output must be mapping".into()), - } let files = read::get_output_files(config); let output_types = vec!["pdf".into()]; for file_def in files.iter() { @@ -66,6 +59,6 @@ pub fn unwrap_group( pub fn validate(config: &Value) -> ValidationResult { return unwrap_group( config, - vec![&check_required_keys, &check_input_files, &check_output_files] + vec![&check_required_keys, &check_config_types, &check_input_files, &check_output_files] ); } diff --git a/src/config/validate_types.rs b/src/config/validate_types.rs new file mode 100644 index 0000000..737e66a --- /dev/null +++ b/src/config/validate_types.rs @@ -0,0 +1,64 @@ +use config::validate::{unwrap_group, ValidationResult}; +use serde_yaml::Value; + + +fn check_root(config: &Value) -> ValidationResult { + if !config.is_mapping() { + return Err("Config should be a mapping".into()); + } + return Ok(()); +} + +fn check_input(config: &Value) -> ValidationResult { + let input = config.get("input").unwrap(); + if !input.is_sequence() { + return Err("Input must be sequence".into()); + } + + if input.as_sequence().into_iter().count() == 0 { + return Err("Must provide input files".into()); + } + + for input_file in input.as_sequence().unwrap() { + if !input_file.is_string() { + return Err("Input must be string".into()); + } + } + return Ok(()); +} + +fn check_output(config: &Value) -> ValidationResult { + let output = config.get("output").unwrap(); + if !output.is_mapping() { + return Err("Output must be mapping".into()); + } + + if output.as_mapping().into_iter().count() == 0 { + return Err("Must provide output files".into()); + } + + for output_def in output.as_mapping().unwrap() { + if !output_def.0.is_string() { + return Err("Output keys must be strings".into()); + } + if !output_def.1.is_string() { + return Err("Output values must be strings".into()); + } + } + return Ok(()); +} + +fn check_title(config: &Value) -> ValidationResult { + if !config.get("title").unwrap().is_string() { + return Err("Title should be a string".into()); + } + return Ok(()); +} + + +pub fn check_config_types(config: &Value) -> ValidationResult { + return unwrap_group( + config, + vec![&check_root, &check_input, &check_output, &check_title] + ); +}