Skip to main content

ember_cluster/
error.rs

1//! Error types for cluster operations.
2
3use std::net::SocketAddr;
4
5use crate::NodeId;
6
7/// Errors that can occur during cluster operations.
8#[derive(Debug, thiserror::Error)]
9pub enum ClusterError {
10    /// The slot is not assigned to any node.
11    #[error("slot {0} is not assigned to any node")]
12    SlotNotAssigned(u16),
13
14    /// The key belongs to a slot on a different node.
15    #[error("MOVED {slot} {addr}")]
16    Moved { slot: u16, addr: SocketAddr },
17
18    /// The slot is being migrated; client should retry with ASK.
19    #[error("ASK {slot} {addr}")]
20    Ask { slot: u16, addr: SocketAddr },
21
22    /// Node not found in the cluster.
23    #[error("node {0} not found in cluster")]
24    NodeNotFound(NodeId),
25
26    /// Cluster is not in a healthy state.
27    #[error("cluster is down")]
28    ClusterDown,
29
30    /// Operation requires a different node role.
31    #[error("operation not supported on {role} node")]
32    WrongRole { role: String },
33
34    /// Cross-slot operation with keys in different slots.
35    #[error("cross-slot keys not allowed (keys span slots {0} and {1})")]
36    CrossSlot(u16, u16),
37
38    /// Network error during cluster communication.
39    #[error("cluster communication error: {0}")]
40    Network(String),
41
42    /// Timeout waiting for cluster operation.
43    #[error("cluster operation timed out")]
44    Timeout,
45
46    /// Configuration error.
47    #[error("invalid cluster configuration: {0}")]
48    Configuration(String),
49}
50
51impl ClusterError {
52    /// Returns true if this is a redirect error (MOVED or ASK).
53    pub fn is_redirect(&self) -> bool {
54        matches!(self, ClusterError::Moved { .. } | ClusterError::Ask { .. })
55    }
56
57    /// Creates a MOVED error for a slot redirect.
58    pub fn moved(slot: u16, addr: SocketAddr) -> Self {
59        ClusterError::Moved { slot, addr }
60    }
61
62    /// Creates an ASK error for a slot migration redirect.
63    pub fn ask(slot: u16, addr: SocketAddr) -> Self {
64        ClusterError::Ask { slot, addr }
65    }
66}