Skip to main content

digdigdig3_station/
error.rs

1use thiserror::Error;
2
3#[derive(Debug, Error)]
4pub enum StationError {
5    #[error("station not yet built")]
6    NotBuilt,
7    #[error("subscription failed: {0}")]
8    Subscribe(String),
9    /// The exchange does not expose this stream on the WS wire. Subscribe
10    /// MUST NOT spawn a forwarder for this combination — heal/resub would
11    /// loop forever. Surfaced from `subscribe_frame` returning either
12    /// `WebSocketError::WireAbsent` or `WebSocketError::NotImplemented`.
13    /// Consumers should treat this as a quiet "skip" rather than a hard
14    /// failure: it's an architectural fact about the venue, not a runtime fault.
15    #[error("stream not supported by exchange: {0}")]
16    StreamNotSupported(String),
17    #[error("core error: {0}")]
18    Core(String),
19    #[error("io error: {0}")]
20    Io(#[from] std::io::Error),
21    /// `Station::rewarm_derived` was asked to deepen a `SeriesKey.kind`
22    /// whose fold state cannot be reconstructed from the already-emitted
23    /// output alone (tick/volume imbalance bars and run bars carry EMA
24    /// state accumulated over the ENTIRE history — there is no
25    /// seed-from-output for that). Callers must fall back to the old
26    /// teardown + resubscribe-at-depth path for these three kinds.
27    #[error("kind does not support prepend-fold rewarm: {0}")]
28    RewarmUnsupported(String),
29}
30
31impl StationError {
32    /// True when this error originates from the venue not exposing the
33    /// requested stream (wire-not-present), as opposed to a transient
34    /// runtime failure. Used by `Station::subscribe(set)` to bucket
35    /// per-stream outcomes in the returned `SubscribeReport`.
36    pub fn is_not_supported(&self) -> bool {
37        matches!(self, StationError::StreamNotSupported(_))
38    }
39}
40
41pub type Result<T> = std::result::Result<T, StationError>;