1use crate::{core::DomainReason, ErrorCategory, ErrorIdentityProvider, StructError};
2
3#[allow(dead_code)]
4pub trait TestAssert {
6 type Output;
7 fn assert(self) -> Self::Output;
8}
9
10#[allow(dead_code)]
11pub trait TestAssertWithMsg<A> {
13 type Output;
14 fn assert(self, msg: A) -> Self::Output;
15}
16
17impl<T, E> TestAssert for Result<T, E>
18where
19 E: std::fmt::Display,
20{
21 type Output = T;
22
23 fn assert(self) -> T {
24 self.unwrap_or_else(|e| panic!("[TEST ASSERTION FAILED] \n Error details: {e}"))
25 }
26}
27
28impl<T, E> TestAssertWithMsg<&str> for Result<T, E>
29where
30 E: std::fmt::Display,
31{
32 type Output = T;
33
34 fn assert(self, msg: &str) -> T {
35 self.unwrap_or_else(|e| panic!("[TEST ASSERTION FAILED] {msg} \n Error details: {e}"))
36 }
37}
38
39impl<T> TestAssert for Option<T> {
40 type Output = T;
41
42 fn assert(self) -> T {
43 self.unwrap_or_else(|| panic!("[OPTION ASSERTION FAILED] ",))
44 }
45}
46
47pub fn assert_err_code<R>(err: &StructError<R>, code: &str)
48where
49 R: DomainReason + ErrorIdentityProvider,
50{
51 assert_eq!(err.reason().stable_code(), code);
52}
53
54pub fn assert_err_category<R>(err: &StructError<R>, category: ErrorCategory)
55where
56 R: DomainReason + ErrorIdentityProvider,
57{
58 assert_eq!(err.reason().error_category(), category);
59}
60
61pub fn assert_err_identity<R>(err: &StructError<R>, code: &str, category: ErrorCategory)
62where
63 R: DomainReason + ErrorIdentityProvider,
64{
65 assert_err_code(err, code);
66 assert_err_category(err, category);
67}
68
69pub fn assert_err_operation<R>(err: &StructError<R>, operation: &str)
70where
71 R: DomainReason,
72{
73 assert_eq!(err.action_main().as_deref(), Some(operation));
74}
75
76pub fn assert_err_path<R>(err: &StructError<R>, path: &str)
77where
78 R: DomainReason,
79{
80 assert_eq!(err.target_path().as_deref(), Some(path));
81}
82
83#[cfg(test)]
84mod tests {
85 use super::{
86 assert_err_category, assert_err_code, assert_err_identity, assert_err_operation,
87 assert_err_path,
88 };
89 use crate::{ErrorCategory, ErrorWith, StructError, UvsReason};
90
91 #[test]
92 fn test_assert_err_code_helper() {
93 let err = StructError::from(UvsReason::system_error());
94 assert_err_code(&err, "sys.io_error");
95 }
96
97 #[test]
98 fn test_assert_err_category_helper() {
99 let err = StructError::from(UvsReason::business_error());
100 assert_err_category(&err, ErrorCategory::Biz);
101 }
102
103 #[test]
104 fn test_assert_err_identity_helper() {
105 let err = StructError::from(UvsReason::network_error());
106 assert_err_identity(&err, "sys.network_error", ErrorCategory::Sys);
107 }
108
109 #[test]
110 fn test_assert_err_operation_helper() {
111 let err = StructError::from(UvsReason::system_error())
112 .with_detail("read config failed")
113 .doing("load config");
114 assert_err_operation(&err, "load config");
115 }
116
117 #[test]
118 fn test_assert_err_path_helper() {
119 let err = StructError::from(UvsReason::system_error())
120 .with_detail("read config failed")
121 .doing("load config")
122 .at("config.toml");
123 assert_err_path(&err, "load config / config.toml");
124 }
125}