use crate::model::ViolationDetails;
const EARLIEST_LTS_SCHEMA_VERSION: &str = "1.11.0";
fn parse_version(version: &str) -> Option<(u32, u32, u32)> {
let parts: Vec<&str> = version.split('.').collect();
if parts.len() != 3 {
return None;
}
let major = parts[0].parse::<u32>().ok()?;
let minor = parts[1].parse::<u32>().ok()?;
let patch = parts[2].parse::<u32>().ok()?;
Some((major, minor, patch))
}
fn is_version_older_than(version: &str, minimum: &str) -> bool {
let Some(ver) = parse_version(version) else {
return false;
};
let Some(min) = parse_version(minimum) else {
return false;
};
ver < min
}
pub fn schema_version_should_be_current<'a>(
data: &'a serde_json::Value,
) -> Option<ViolationDetails> {
let schema_version = data.get("schema_version").and_then(|sv| sv.as_str());
let Some(schema_version) = schema_version else {
return Some(ViolationDetails { details: None });
};
if is_version_older_than(schema_version, EARLIEST_LTS_SCHEMA_VERSION) {
return Some(ViolationDetails {
details: Some(format!(
"schema_version={}, earliest_supported={}",
schema_version, EARLIEST_LTS_SCHEMA_VERSION
)),
});
}
None
}
#[cfg(test)]
mod tests {
use super::*;
use serde_json::json;
#[test]
fn test_parse_version_valid() {
assert_eq!(parse_version("1.11.0"), Some((1, 11, 0)));
assert_eq!(parse_version("2.0.0"), Some((2, 0, 0)));
assert_eq!(parse_version("1.10.5"), Some((1, 10, 5)));
}
#[test]
fn test_parse_version_invalid() {
assert_eq!(parse_version("1.11"), None);
assert_eq!(parse_version("1.11.0.0"), None);
assert_eq!(parse_version("invalid"), None);
assert_eq!(parse_version("1.a.0"), None);
}
#[test]
fn test_is_version_older_than() {
assert!(is_version_older_than("1.10.0", "1.11.0"));
assert!(is_version_older_than("1.9.5", "1.11.0"));
assert!(is_version_older_than("0.9.0", "1.11.0"));
assert!(!is_version_older_than("1.11.0", "1.11.0"));
assert!(!is_version_older_than("1.12.0", "1.11.0"));
assert!(!is_version_older_than("2.0.0", "1.11.0"));
assert!(!is_version_older_than("1.11.1", "1.11.0"));
}
#[test]
fn test_schema_version_too_old() {
let data = json!({
"schema_version": "1.10.0"
});
let result = schema_version_should_be_current(&data);
assert!(result.is_some());
let details = result.unwrap().details.unwrap();
assert!(details.contains("1.10.0"));
assert!(details.contains("1.11.0"));
}
#[test]
fn test_schema_version_at_earliest_lts() {
let data = json!({
"schema_version": "1.11.0"
});
let result = schema_version_should_be_current(&data);
assert!(result.is_none());
}
#[test]
fn test_schema_version_newer_than_lts() {
let data = json!({
"schema_version": "2.0.0"
});
let result = schema_version_should_be_current(&data);
assert!(result.is_none());
}
#[test]
fn test_schema_version_missing() {
let data = json!({});
let result = schema_version_should_be_current(&data);
assert!(result.is_some());
assert!(result.unwrap().details.is_none());
}
}