use std::path::{Path, PathBuf};
fn repo_root() -> PathBuf {
Path::new(env!("CARGO_MANIFEST_DIR")).join("..").join("..")
}
const PAIRS: &[(&str, &str)] = &[
("CHANGELOG.md", "CHANGELOG.md"),
("README.md", "README.md"),
(
"Administrator_Guide.md",
"documentation/Administrator_Guide.md",
),
("User_Guide.md", "documentation/User_Guide.md"),
];
#[test]
fn every_embedded_doc_matches_its_source() {
let root = repo_root();
let embedded_dir = Path::new(env!("CARGO_MANIFEST_DIR")).join("embedded_docs");
let mut compared = 0_usize;
for (embedded_name, source_rel) in PAIRS {
let source = root.join(source_rel);
if !source.is_file() {
continue;
}
let embedded_path = embedded_dir.join(embedded_name);
let embedded = std::fs::read_to_string(&embedded_path).unwrap_or_else(|e| {
panic!("{embedded_name} is embedded by info.rs but unreadable: {e}")
});
let expected = std::fs::read_to_string(&source)
.unwrap_or_else(|e| panic!("{source_rel} unreadable: {e}"));
assert_eq!(
embedded, expected,
"\n\
embedded_docs/{embedded_name} has drifted from {source_rel}.\n\
The server would serve the STALE copy — the mismatch is invisible\n\
at runtime because both files compile and all other tests pass.\n\
Re-sync with:\n \
cp -f -p -v {source_rel} crates/csaf-crud/embedded_docs/{embedded_name}\n"
);
compared += 1;
}
if root.join("CHANGELOG.md").is_file() {
assert_eq!(
compared,
PAIRS.len(),
"expected to compare all {} embedded documents, compared {compared}",
PAIRS.len(),
);
}
}
#[test]
fn every_embedded_file_is_covered_by_this_test() {
let embedded_dir = Path::new(env!("CARGO_MANIFEST_DIR")).join("embedded_docs");
let entries = std::fs::read_dir(&embedded_dir).expect("embedded_docs must exist");
for entry in entries {
let entry = entry.expect("readable dir entry");
let name = entry.file_name().to_string_lossy().into_owned();
let is_markdown = Path::new(&name)
.extension()
.is_some_and(|ext| ext.eq_ignore_ascii_case("md"));
if !is_markdown {
continue;
}
assert!(
PAIRS.iter().any(|(embedded, _)| *embedded == name),
"embedded_docs/{name} is shipped but has no entry in PAIRS, so nothing \
checks it for drift — add it to PAIRS in this file",
);
}
}