1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
use crate::config::Config;
use ansi_term::Colour::{Green, Red};
use anyhow::{anyhow, Result};
use std::path::{Path, PathBuf};
use walkdir::WalkDir;

/// Validate the target PathBuf
pub fn validate_target(target: &Path) -> Result<()> {
    let target = PathBuf::from(target);

    if !target.exists() {
        return Err(anyhow!(
            "{:?} ... {} - file/directory does not exist",
            target,
            Red.paint("Failed")
        ));
    }

    // Scan all files recursive from current directory
    // that match *.yaml or *.yml and validate them
    if target.is_dir() {
        let mut files = vec![];
        for entry in WalkDir::new(target) {
            let entry = entry?;
            if entry.path().is_file() {
                let file_name = entry.path().file_name().unwrap();
                if file_name.to_str().unwrap().ends_with(".yaml")
                    || file_name.to_str().unwrap().ends_with(".yml")
                {
                    let path = entry.path().to_path_buf();
                    files.push(path);
                }
            }
        }

        for file in files {
            // Validate but not panic
            validate_file(&file).unwrap_or_else(|e| {
                println!("{}", e);
            });
        }

        return Ok(());
    }

    // Validate single file
    validate_file(&target)
}

/// Validate target yaml file
pub fn validate_file(file: &Path) -> Result<()> {
    let file = PathBuf::from(file);
    let value = Config::new(&file)
        .map_err(|e| anyhow!("{:?} ... {} - {}", file, Red.paint("invalid"), e))?;

    value
        .validate()
        .map_err(|e| anyhow!("{:?} ... {} - {}", file, Red.paint("invalid"), e))?;

    // "OK" in green color
    println!("{:?} ... {}", file, Green.paint("ok"));

    Ok(())
}