iop_morpheus_proto/data/
validation.rs1use serde::{Deserialize, Serialize};
2
3#[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, Ord, PartialOrd, PartialEq, Serialize)]
4pub enum ValidationStatus {
5 Valid,
7 MaybeValid,
11 Invalid,
13}
14
15impl std::fmt::Display for ValidationStatus {
16 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
17 let msg = match self {
18 Self::Valid => "valid",
19 Self::MaybeValid => "maybe valid",
20 Self::Invalid => "invalid",
21 };
22 write!(f, "{}", msg)
23 }
24}
25
26#[derive(Clone, Copy, Debug, Deserialize, Eq, Hash, Ord, PartialOrd, PartialEq, Serialize)]
27pub enum ValidationIssueSeverity {
28 Warning,
29 Error,
30}
31
32impl std::fmt::Display for ValidationIssueSeverity {
33 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
34 let msg = match self {
35 Self::Warning => "warning",
36 Self::Error => "error",
37 };
38 write!(f, "{}", msg)
39 }
40}
41
42const VALIDATION_CODE_DEFAULT: u32 = 0;
43
44#[derive(Clone, Debug, Deserialize, Eq, Hash, Ord, PartialOrd, PartialEq, Serialize)]
45pub struct ValidationIssue {
46 code: u32,
47 reason: String,
48 severity: ValidationIssueSeverity,
49}
50
51impl ValidationIssue {
52 pub fn code(&self) -> u32 {
53 self.code
54 }
55 pub fn reason(&self) -> &str {
56 &self.reason
57 }
58 pub fn severity(&self) -> ValidationIssueSeverity {
59 self.severity
60 }
61}
62
63#[derive(Clone, Debug, Default, Deserialize, Eq, Hash, Ord, PartialOrd, PartialEq, Serialize)]
64pub struct ValidationResult {
65 issues: Vec<ValidationIssue>,
66}
67
68impl ValidationResult {
69 pub fn status(&self) -> ValidationStatus {
70 let has_error = self.issues.iter().any(|it| it.severity == ValidationIssueSeverity::Error);
71 if has_error {
72 ValidationStatus::Invalid
73 } else if !self.issues.is_empty() {
74 ValidationStatus::MaybeValid
75 } else {
76 ValidationStatus::Valid
77 }
78 }
79
80 pub fn add_issue(&mut self, severity: ValidationIssueSeverity, reason: &str) {
81 self.issues.push(ValidationIssue {
82 severity,
83 code: VALIDATION_CODE_DEFAULT,
84 reason: reason.to_owned(),
85 })
86 }
87
88 pub fn issues(&self) -> &[ValidationIssue] {
89 self.issues.as_slice()
90 }
91}