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
|
use crate::Configuration;
use std::collections::HashSet;
fn check_configs_equal(
cfg1: &Configuration,
cfg2: &Configuration,
) -> Result<(), Box<dyn std::error::Error>> {
let keys1: HashSet<&str> = cfg1.iter().map(|(k, _)| k).collect();
let keys2: HashSet<&str> = cfg2.iter().map(|(k, _)| k).collect();
for key in keys1.difference(&keys2) {
return Err(format!(
"Key {key} appears at {}, but not in other configuration",
cfg1.location(&key).unwrap()
)
.into());
}
for key in keys2.difference(&keys1) {
return Err(format!(
"Key {key} appears at {}, but not in other configuration",
cfg2.location(&key).unwrap()
)
.into());
}
for (key, val1) in cfg1.iter() {
let val2 = cfg2.get(&key).unwrap();
if val1 != val2 {
return Err(format!(
"Mismatch between values for key {key}
defined as {val1:?} at {},
but defined as {val2:?} at {}",
cfg1.location(&key)
.map_or("<nowhere>".into(), |x| format!("{x}")),
cfg2.location(&key)
.map_or("<nowhere>".into(), |x| format!("{x}")),
)
.into());
}
}
Ok(())
}
#[test]
fn parsing() {
super::do_tests_in_dir("parsing", ".flat.pom", |filename| {
let config1 = Configuration::load_path(filename)?;
let config2 = Configuration::load_path(&filename.replace(".flat.pom", ".pom"))?;
check_configs_equal(&config1, &config2)
})
}
|