Skip to main content

yog_cli/
script.rs

1//! A mod's Yog Script (`src/**/*.ys`, `*.yns`): each source checked by the
2//! compiler (`yog-script-build`), what's wrong reported at its file, line
3//! and column; errors stop the build.
4
5use std::path::Path;
6
7use yog_ids::Format;
8
9use crate::diagnostics;
10
11/// Where a mod's code is: its scripts beside its Rust.
12const SOURCES: &str = "src";
13
14/// Checks every script of the mod at `root`; an error when one has errors.
15pub fn check(root: &Path) -> Result<(), String> {
16    let dir = root.join(SOURCES);
17    let mut errors = 0;
18    for format in [Format::Script, Format::Nanites] {
19        for file in crate::files::of(&dir, format) {
20            let text =
21                std::fs::read_to_string(&file).map_err(|e| format!("{}: {e}", file.display()))?;
22            let name = crate::shown_path(root, &file);
23            let problems = yog_script_build::check_source(&name, &text);
24            errors += problems.iter().filter(|d| d.is_error()).count();
25            diagnostics::report_all(&problems);
26            for d in &problems {
27                match d.is_error() {
28                    true => yog_logging::error!("{d}"),
29                    false => yog_logging::warn!("{d}"),
30                }
31            }
32        }
33    }
34    match errors {
35        0 => Ok(()),
36        n => Err(format!("{n} error(s) in the mod's Yog Script")),
37    }
38}
39
40#[cfg(test)]
41mod tests {
42    use super::*;
43
44    #[test]
45    fn a_mods_scripts_are_checked() {
46        let root = std::env::temp_dir().join(format!("yog-script-check-{}", std::process::id()));
47        let src = root.join(SOURCES).join("power");
48        std::fs::create_dir_all(&src).unwrap();
49        std::fs::write(src.join("ok.ys"), "int Area(int w, int h) => w * h;\n").unwrap();
50        assert_eq!(check(&root), Ok(()));
51        std::fs::write(src.join("bad.ys"), "void F() {\n    break;\n}\n").unwrap();
52        assert!(check(&root).is_err());
53        std::fs::remove_dir_all(&root).unwrap();
54    }
55}