1use std::fmt;
4
5#[derive(Debug)]
7pub enum WebSocketError {
8 InvalidUpgrade(String),
10 HandshakeFailed(String),
12 ConnectionClosed,
14 SendFailed(String),
16 ReceiveFailed(String),
18 SerializationError(String),
20 DeserializationError(String),
22 ProtocolError(String),
24 IoError(std::io::Error),
26 Tungstenite(tungstenite::Error),
28}
29
30impl fmt::Display for WebSocketError {
31 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
32 match self {
33 Self::InvalidUpgrade(msg) => write!(f, "Invalid WebSocket upgrade request: {}", msg),
34 Self::HandshakeFailed(msg) => write!(f, "WebSocket handshake failed: {}", msg),
35 Self::ConnectionClosed => write!(f, "Connection closed unexpectedly"),
36 Self::SendFailed(msg) => write!(f, "Failed to send message: {}", msg),
37 Self::ReceiveFailed(msg) => write!(f, "Failed to receive message: {}", msg),
38 Self::SerializationError(msg) => write!(f, "Message serialization error: {}", msg),
39 Self::DeserializationError(msg) => write!(f, "Message deserialization error: {}", msg),
40 Self::ProtocolError(msg) => write!(f, "WebSocket protocol error: {}", msg),
41 Self::IoError(e) => write!(f, "IO error: {}", e),
42 Self::Tungstenite(e) => write!(f, "WebSocket error: {}", e),
43 }
44 }
45}
46
47impl std::error::Error for WebSocketError {
48 fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
49 match self {
50 Self::IoError(e) => Some(e),
51 Self::Tungstenite(e) => Some(e),
52 _ => None,
53 }
54 }
55}
56
57impl From<std::io::Error> for WebSocketError {
58 fn from(e: std::io::Error) -> Self {
59 Self::IoError(e)
60 }
61}
62
63impl From<tungstenite::Error> for WebSocketError {
64 fn from(e: tungstenite::Error) -> Self {
65 Self::Tungstenite(e)
66 }
67}
68
69impl WebSocketError {
70 pub fn invalid_upgrade(msg: impl Into<String>) -> Self {
72 Self::InvalidUpgrade(msg.into())
73 }
74
75 pub fn handshake_failed(msg: impl Into<String>) -> Self {
77 Self::HandshakeFailed(msg.into())
78 }
79
80 pub fn send_failed(msg: impl Into<String>) -> Self {
82 Self::SendFailed(msg.into())
83 }
84
85 pub fn receive_failed(msg: impl Into<String>) -> Self {
87 Self::ReceiveFailed(msg.into())
88 }
89
90 pub fn serialization_error(msg: impl Into<String>) -> Self {
92 Self::SerializationError(msg.into())
93 }
94
95 pub fn deserialization_error(msg: impl Into<String>) -> Self {
97 Self::DeserializationError(msg.into())
98 }
99
100 pub fn protocol_error(msg: impl Into<String>) -> Self {
102 Self::ProtocolError(msg.into())
103 }
104}
105
106impl From<WebSocketError> for rustapi_core::ApiError {
107 fn from(err: WebSocketError) -> Self {
108 match err {
109 WebSocketError::InvalidUpgrade(msg) => {
110 rustapi_core::ApiError::bad_request(format!("WebSocket upgrade failed: {}", msg))
111 }
112 WebSocketError::HandshakeFailed(msg) => {
113 rustapi_core::ApiError::bad_request(format!("WebSocket handshake failed: {}", msg))
114 }
115 _ => rustapi_core::ApiError::internal(err.to_string()),
116 }
117 }
118}
119
120impl From<crate::auth::AuthError> for rustapi_core::ApiError {
121 fn from(err: crate::auth::AuthError) -> Self {
122 match err {
123 crate::auth::AuthError::TokenMissing => {
124 rustapi_core::ApiError::unauthorized("Authentication token missing")
125 }
126 crate::auth::AuthError::TokenExpired => {
127 rustapi_core::ApiError::unauthorized("Token has expired")
128 }
129 crate::auth::AuthError::InvalidSignature => {
130 rustapi_core::ApiError::unauthorized("Invalid token signature")
131 }
132 crate::auth::AuthError::InvalidFormat(msg) => {
133 rustapi_core::ApiError::bad_request(format!("Invalid token format: {}", msg))
134 }
135 crate::auth::AuthError::ValidationFailed(msg) => {
136 rustapi_core::ApiError::unauthorized(format!("Token validation failed: {}", msg))
137 }
138 crate::auth::AuthError::InsufficientPermissions(msg) => {
139 rustapi_core::ApiError::forbidden(format!("Insufficient permissions: {}", msg))
140 }
141 }
142 }
143}