1use thiserror::Error;
4
5#[derive(Debug, Error)]
7pub enum McpAuthError {
8 #[error("missing DAT token: {0}")]
10 MissingToken(String),
11
12 #[error("invalid DAT: {0}")]
14 InvalidDat(String),
15
16 #[error("insufficient scope: {0}")]
18 InsufficientScope(String),
19
20 #[error("verification failed: {0}")]
22 VerificationFailed(String),
23}
24
25impl From<idprova_core::IdprovaError> for McpAuthError {
26 fn from(e: idprova_core::IdprovaError) -> Self {
27 match &e {
28 idprova_core::IdprovaError::ScopeNotPermitted(_) => {
29 McpAuthError::InsufficientScope(e.to_string())
30 }
31 idprova_core::IdprovaError::InvalidDat(_) => McpAuthError::InvalidDat(e.to_string()),
32 idprova_core::IdprovaError::DatExpired | idprova_core::IdprovaError::DatNotYetValid => {
33 McpAuthError::VerificationFailed(e.to_string())
34 }
35 _ => McpAuthError::VerificationFailed(e.to_string()),
36 }
37 }
38}
39
40#[cfg(test)]
41mod tests {
42 use super::*;
43
44 #[test]
45 fn test_error_display_missing_token() {
46 let e = McpAuthError::MissingToken("no token".into());
47 assert!(e.to_string().contains("missing DAT token"));
48 }
49
50 #[test]
51 fn test_error_display_invalid_dat() {
52 let e = McpAuthError::InvalidDat("bad format".into());
53 assert!(e.to_string().contains("invalid DAT"));
54 }
55
56 #[test]
57 fn test_error_display_insufficient_scope() {
58 let e = McpAuthError::InsufficientScope("need write".into());
59 assert!(e.to_string().contains("insufficient scope"));
60 }
61
62 #[test]
63 fn test_error_display_verification_failed() {
64 let e = McpAuthError::VerificationFailed("expired".into());
65 assert!(e.to_string().contains("verification failed"));
66 }
67
68 #[test]
69 fn test_from_idprova_scope_error() {
70 let core_err = idprova_core::IdprovaError::ScopeNotPermitted("write denied".into());
71 let mcp_err: McpAuthError = core_err.into();
72 assert!(matches!(mcp_err, McpAuthError::InsufficientScope(_)));
73 }
74
75 #[test]
76 fn test_from_idprova_invalid_dat() {
77 let core_err = idprova_core::IdprovaError::InvalidDat("malformed".into());
78 let mcp_err: McpAuthError = core_err.into();
79 assert!(matches!(mcp_err, McpAuthError::InvalidDat(_)));
80 }
81
82 #[test]
83 fn test_from_idprova_expired() {
84 let core_err = idprova_core::IdprovaError::DatExpired;
85 let mcp_err: McpAuthError = core_err.into();
86 assert!(matches!(mcp_err, McpAuthError::VerificationFailed(_)));
87 }
88}