use dbgen::{
cli::{run, Args},
span::Registry,
};
use diff::{lines, Result as DiffResult};
use serde_json::from_reader;
use std::{
env,
error::Error,
ffi::OsStr,
fs::{read, read_dir, remove_file, File},
path::Path,
str::from_utf8,
};
use tempfile::tempdir;
#[test]
fn run_test() {
main().unwrap();
}
fn main() -> Result<(), Box<dyn Error>> {
let out_dir = tempdir()?;
let no_print_diff = env::var_os("DIFF").as_deref() == Some(OsStr::new("0"));
let data_dir = Path::new(file!()).with_file_name("data");
let zoneinfo_dir = Path::new(file!()).with_file_name("zoneinfo");
let mut content_differed = false;
for child_dir in read_dir(data_dir)? {
let child_dir = child_dir?;
if !child_dir.file_type()?.is_dir() {
continue;
}
let child_path = child_dir.path();
eprintln!("Running {}...", child_path.display());
let mut args: Args = from_reader(File::open(child_path.join("flags.json"))?)?;
args.template = child_path.join("template.sql");
args.out_dir = out_dir.path().to_owned();
args.zoneinfo = zoneinfo_dir.clone();
let mut registry = Registry::default();
run(args, &mut registry)?;
for result_entry in read_dir(out_dir.path())? {
let result_entry = result_entry?;
let expected_path = child_path.join(result_entry.file_name());
let actual_path = result_entry.path();
eprintln!("Comparing {} vs {} ...", expected_path.display(), actual_path.display());
let expected_content = read(expected_path)?;
let actual_content = read(&actual_path)?;
if expected_content != actual_content {
content_differed = true;
let expected_string = from_utf8(&expected_content)?;
let actual_string = from_utf8(&actual_content)?;
if no_print_diff {
eprintln!("\x1b[32m{}\x1b[0m", actual_string);
} else {
for diff in lines(&expected_string, &actual_string) {
match diff {
DiffResult::Left(missing) => {
eprintln!("\x1b[31m- {}\x1b[0m", missing);
}
DiffResult::Right(unexpected) => {
eprintln!("\x1b[32m+ {}\x1b[0m", unexpected);
}
DiffResult::Both(same, _) => {
eprintln!(" {}", same);
}
}
}
}
}
remove_file(actual_path)?;
}
}
assert!(!content_differed);
Ok(())
}