use super::CheckViolation;
#[derive(Debug, Clone, Copy, PartialEq, Eq, serde::Serialize)]
pub enum Severity {
Error,
Warning,
}
#[derive(Debug, Default, Clone, PartialEq, Eq)]
pub struct Violations(Vec<CheckViolation>);
impl Violations {
pub fn new() -> Self {
Self::default()
}
pub fn push(&mut self, v: CheckViolation) {
self.0.push(v);
}
pub fn extend(&mut self, other: Violations) {
self.0.extend(other.0);
}
pub fn is_empty(&self) -> bool {
self.0.is_empty()
}
pub fn has_errors(&self) -> bool {
self.0.iter().any(|v| v.severity == Severity::Error)
}
pub fn iter(&self) -> impl Iterator<Item = &CheckViolation> {
self.0.iter()
}
}
impl IntoIterator for Violations {
type Item = CheckViolation;
type IntoIter = std::vec::IntoIter<CheckViolation>;
fn into_iter(self) -> Self::IntoIter {
self.0.into_iter()
}
}
impl<'a> IntoIterator for &'a Violations {
type Item = &'a CheckViolation;
type IntoIter = std::slice::Iter<'a, CheckViolation>;
fn into_iter(self) -> Self::IntoIter {
self.0.iter()
}
}
impl FromIterator<CheckViolation> for Violations {
fn from_iter<I: IntoIterator<Item = CheckViolation>>(iter: I) -> Self {
Violations(iter.into_iter().collect())
}
}
#[cfg(test)]
pub mod strategy {
use super::{Severity, Violations};
use crate::domain::model::check::check_violation::strategy::check_violation;
use proptest::prelude::*;
pub fn severity() -> impl Strategy<Value = Severity> {
prop_oneof![Just(Severity::Error), Just(Severity::Warning)]
}
pub fn violations() -> impl Strategy<Value = Violations> {
proptest::collection::vec(check_violation(), 0..=4).prop_map(|v| v.into_iter().collect())
}
}
#[cfg(test)]
mod tests {
use super::*;
use proptest::prelude::*;
proptest! {
#[test]
fn has_errors_matches_any_error_severity(vs in strategy::violations()) {
let any_error = vs.iter().any(|v| v.severity == Severity::Error);
prop_assert_eq!(vs.has_errors(), any_error);
}
}
}