1#![allow(missing_docs)]
3
4use crate::boundary::BoundaryError;
12use soma_som_core::error::SomaError;
13use soma_som_core::extension::GateRejection;
14use soma_som_core::types::UnitId;
15
16#[derive(Debug, thiserror::Error)]
22#[non_exhaustive]
23pub enum RingEngineError {
24 #[error("Ring engine not initialized — run genesis first")]
27 NotInitialized,
28
29 #[error("Genesis already completed — ring is in standard operation")]
31 GenesisAlreadyComplete,
32
33 #[error("Unit {unit} processing failed: {reason}")]
40 ProcessorFailed { unit: UnitId, reason: String },
41
42 #[error("Unit {unit} is disabled — no processor registered")]
44 UnitDisabled { unit: UnitId },
45
46 #[error("Cycle rejected by BEFORE gate: {0}")]
49 GateRejected(#[from] GateRejection),
50
51 #[error("Boundary error: {0}")]
54 Boundary(#[from] BoundaryError),
55
56 #[error("Core error: {0}")]
58 Core(#[from] SomaError),
59
60 #[error("Cycle {cycle_index} failed: {reason}")]
63 CycleFailed { cycle_index: u64, reason: String },
64}
65
66pub type RingEngineResult<T> = Result<T, RingEngineError>;
68
69#[cfg(test)]
71mod tests {
72 use super::*;
73
74 #[test]
75 fn error_display_not_initialized() {
76 let e = RingEngineError::NotInitialized;
77 assert!(e.to_string().contains("not initialized"));
78 }
79
80 #[test]
81 fn error_display_processor_failed() {
82 let e = RingEngineError::ProcessorFailed {
83 unit: UnitId::FU,
84 reason: "timeout".into(),
85 };
86 assert!(e.to_string().contains("FU"));
87 assert!(e.to_string().contains("timeout"));
88 }
89
90 #[test]
91 fn error_display_unit_disabled() {
92 let e = RingEngineError::UnitDisabled { unit: UnitId::CU };
93 assert!(e.to_string().contains("CU"));
94 assert!(e.to_string().contains("disabled"));
95 }
96
97 #[test]
98 fn error_display_gate_rejected() {
99 let rejection = GateRejection {
100 source: "guard".into(),
101 reason: "rate limit".into(),
102 };
103 let e = RingEngineError::GateRejected(rejection);
104 assert!(e.to_string().contains("guard"));
105 }
106
107 #[test]
108 fn error_display_cycle_failed() {
109 let e = RingEngineError::CycleFailed {
110 cycle_index: 42,
111 reason: "integrity".into(),
112 };
113 assert!(e.to_string().contains("42"));
114 }
115}