Skip to main content

Mountain/Error/
IPCError.rs

1//! # IPC Error Types
2//!
3//! IPC-specific error types for Mountain.
4//! Covers connection establishment, message send and receive,
5//! format validation, operation timeout, permission checks,
6//! service availability, and queue capacity.
7
8use std::{error::Error as StdError, fmt};
9
10use serde::{Deserialize, Serialize};
11
12use super::CoreError::{ErrorContext, ErrorKind, ErrorSeverity, MountainError};
13
14/// IPC-specific error types.
15#[derive(Debug, Clone, Serialize, Deserialize)]
16pub enum IPCError {
17	/// Connection failed.
18	ConnectionFailed { context:ErrorContext, source:Option<String> },
19
20	/// Message send failed.
21	MessageSendFailed { context:ErrorContext, message_id:Option<String> },
22
23	/// Message receive failed.
24	MessageReceiveFailed { context:ErrorContext, source:Option<String> },
25
26	/// Invalid message format.
27	InvalidMessageFormat { context:ErrorContext, raw_message:Option<String> },
28
29	/// Timeout occurred.
30	Timeout { context:ErrorContext, operation:Option<String>, timeout_ms:u64 },
31
32	/// Permission denied.
33	PermissionDenied { context:ErrorContext, required_permission:Option<String> },
34
35	/// Service unavailable.
36	ServiceUnavailable { context:ErrorContext, service_name:Option<String> },
37
38	/// Queue overflow.
39	QueueOverflow { context:ErrorContext, queue_size:usize },
40}
41
42impl IPCError {
43	/// Get the error context.
44	pub fn context(&self) -> &ErrorContext {
45		match self {
46			IPCError::ConnectionFailed { context, .. } => context,
47
48			IPCError::MessageSendFailed { context, .. } => context,
49
50			IPCError::MessageReceiveFailed { context, .. } => context,
51
52			IPCError::InvalidMessageFormat { context, .. } => context,
53
54			IPCError::Timeout { context, .. } => context,
55
56			IPCError::PermissionDenied { context, .. } => context,
57
58			IPCError::ServiceUnavailable { context, .. } => context,
59
60			IPCError::QueueOverflow { context, .. } => context,
61		}
62	}
63
64	/// Create a connection failed error.
65	pub fn connection_failed(message:impl Into<String>) -> Self {
66		Self::ConnectionFailed {
67			context:ErrorContext::new(message)
68				.with_kind(ErrorKind::IPC)
69				.with_severity(ErrorSeverity::Error),
70
71			source:None,
72		}
73	}
74
75	/// Create a message send failed error.
76	pub fn message_send_failed(message:impl Into<String>, message_id:Option<String>) -> Self {
77		Self::MessageSendFailed {
78			context:ErrorContext::new(message)
79				.with_kind(ErrorKind::IPC)
80				.with_severity(ErrorSeverity::Error),
81
82			message_id,
83		}
84	}
85
86	/// Create a timeout error.
87	pub fn timeout(operation:impl Into<String>, timeout_ms:u64) -> Self {
88		let operation_str = operation.into();
89
90		Self::Timeout {
91			context:ErrorContext::new(format!("Operation timed out after {}ms", timeout_ms))
92				.with_kind(ErrorKind::IPC)
93				.with_severity(ErrorSeverity::Error)
94				.with_operation(operation_str.clone()),
95
96			operation:Some(operation_str),
97
98			timeout_ms,
99		}
100	}
101
102	/// Create a permission denied error.
103	pub fn permission_denied(message:impl Into<String>, required_permission:Option<String>) -> Self {
104		Self::PermissionDenied {
105			context:ErrorContext::new(message)
106				.with_kind(ErrorKind::IPC)
107				.with_severity(ErrorSeverity::Critical),
108
109			required_permission,
110		}
111	}
112
113	/// Create a service unavailable error.
114	pub fn service_unavailable(message:impl Into<String>, service_name:Option<String>) -> Self {
115		Self::ServiceUnavailable {
116			context:ErrorContext::new(message)
117				.with_kind(ErrorKind::IPC)
118				.with_severity(ErrorSeverity::Error),
119
120			service_name,
121		}
122	}
123}
124
125impl fmt::Display for IPCError {
126	fn fmt(&self, f:&mut fmt::Formatter<'_>) -> fmt::Result { write!(f, "{}", self.context()) }
127}
128
129impl StdError for IPCError {}
130
131impl From<IPCError> for MountainError {
132	fn from(err:IPCError) -> Self { MountainError::new(err.context().clone()).with_source(err.to_string()) }
133}