vellaveto_engine/
error.rs1use thiserror::Error;
13
14#[derive(Error, Debug)]
16pub enum EngineError {
17 #[error("No policies defined")]
19 NoPolicies,
20
21 #[error("Evaluation error: {0}")]
23 EvaluationError(String),
24
25 #[error("Invalid condition in policy '{policy_id}': {reason}")]
27 InvalidCondition {
28 policy_id: String,
30 reason: String,
32 },
33
34 #[error("JSON error: {0}")]
36 JsonError(#[from] serde_json::Error),
37
38 #[error("Path normalization failed (fail-closed): {reason}")]
40 PathNormalization {
41 reason: String,
43 },
44}
45
46#[derive(Debug, Clone)]
51pub struct PolicyValidationError {
52 pub policy_id: String,
54 pub policy_name: String,
56 pub reason: String,
58}
59
60impl std::fmt::Display for PolicyValidationError {
61 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
62 write!(
63 f,
64 "Policy '{}' ({}): {}",
65 self.policy_name, self.policy_id, self.reason
66 )
67 }
68}
69
70impl std::error::Error for PolicyValidationError {}
71
72#[cfg(test)]
73mod tests {
74 use super::*;
75
76 #[test]
77 fn test_engine_error_display() {
78 let err = EngineError::NoPolicies;
79 assert_eq!(err.to_string(), "No policies defined");
80
81 let err = EngineError::EvaluationError("test error".to_string());
82 assert_eq!(err.to_string(), "Evaluation error: test error");
83
84 let err = EngineError::InvalidCondition {
85 policy_id: "p1".to_string(),
86 reason: "bad pattern".to_string(),
87 };
88 assert_eq!(
89 err.to_string(),
90 "Invalid condition in policy 'p1': bad pattern"
91 );
92
93 let err = EngineError::PathNormalization {
94 reason: "null byte".to_string(),
95 };
96 assert_eq!(
97 err.to_string(),
98 "Path normalization failed (fail-closed): null byte"
99 );
100 }
101
102 #[test]
103 fn test_policy_validation_error_display() {
104 let err = PolicyValidationError {
105 policy_id: "p1".to_string(),
106 policy_name: "Test Policy".to_string(),
107 reason: "invalid regex".to_string(),
108 };
109 assert_eq!(err.to_string(), "Policy 'Test Policy' (p1): invalid regex");
110 }
111}