docker_puzzles/
puzzles_parser.rs

1use crate::error::UserError;
2use crate::fs_handler;
3use std::collections::HashMap;
4use std::error::Error;
5use yaml_rust::{Yaml, YamlLoader};
6
7pub fn get_puzzles(path: &str) -> Result<HashMap<String, String>, Box<dyn Error>> {
8    let puzzles_paths = fs_handler::collect_files(path, "Puzzles.yml")?;
9
10    let mut puzzles: HashMap<String, String> = HashMap::new();
11    for puzzles_path in &puzzles_paths {
12        let puzzles_content = fs_handler::read_file(puzzles_path)?;
13        let parsed_puzzles = parse_puzzles(puzzles_content.as_str())?;
14        puzzles.extend(parsed_puzzles);
15    }
16
17    Ok(puzzles)
18}
19
20fn parse_puzzles(contents: &str) -> Result<HashMap<String, String>, Box<dyn Error>> {
21    let mut docs = YamlLoader::load_from_str(&contents)?;
22    let doc = docs.pop().unwrap();
23    let entries = match doc {
24        Yaml::Hash(doc) => doc,
25        _ => return Err(UserError::boxed("Unsupported Puzzles.yml structure")),
26    };
27
28    let mut puzzles: HashMap<String, String> = HashMap::new();
29    for (key, value) in &entries {
30        let key = match key {
31            Yaml::String(key) => key.to_string(),
32            _ => return Err(UserError::boxed("Unsupported Puzzles.yml key")),
33        };
34        let value = match value {
35            Yaml::String(value) => value.replace("\\", "\\\n   "),
36            _ => return Err(UserError::boxed("Unsupported Puzzles.yml value")),
37        };
38        puzzles.insert(key, value);
39    }
40
41    Ok(puzzles)
42}
43
44#[cfg(test)]
45mod tests {
46    use super::*;
47
48    #[test]
49    fn it_gets_puzzles() {
50        let puzzles = get_puzzles("./assets").unwrap();
51        let key = String::from("echos");
52        let value = String::from("RUN echo \'a\' \\\n    && echo \'b\'");
53        assert_eq!(
54            [(key, value)]
55                .iter()
56                .cloned()
57                .collect::<HashMap<String, String>>(),
58            puzzles
59        );
60    }
61}