exocore_store/
error.rs

1use std::time::Duration;
2
3#[derive(Debug, thiserror::Error)]
4pub enum Error {
5    #[error("Query parsing error: {0}")]
6    QueryParsing(#[source] anyhow::Error),
7
8    #[cfg(feature = "local")]
9    #[error("Error in Tantivy: {0}")]
10    Tantivy(#[from] tantivy::TantivyError),
11
12    #[cfg(feature = "local")]
13    #[error("Error opening Tantivy directory: {0:?}")]
14    TantivyOpenDirectoryError(#[from] tantivy::directory::error::OpenDirectoryError),
15
16    #[cfg(feature = "local")]
17    #[error("Error parsing Tantivy query: {0:?}")]
18    TantitvyQueryParsing(#[from] tantivy::query::QueryParserError),
19
20    #[cfg(feature = "local")]
21    #[error("Chain engine error: {0}")]
22    ChainEngine(#[from] exocore_chain::engine::EngineError),
23
24    #[cfg(feature = "local")]
25    #[error("Chain error: {0}")]
26    Chain(#[from] exocore_chain::chain::Error),
27
28    #[cfg(feature = "local")]
29    #[error("Chain block error: {0}")]
30    ChainBlock(#[from] exocore_chain::block::Error),
31
32    #[cfg(feature = "remote")]
33    #[error("Transport error: {0}")]
34    Transport(#[from] exocore_transport::Error),
35
36    #[error("Error in capnp serialization: {0}")]
37    Serialization(#[from] exocore_protos::capnp::Error),
38
39    #[error("Protobuf error: {0}")]
40    Proto(#[from] exocore_protos::Error),
41
42    #[error("A protobuf field was expected, but was empty: {0}")]
43    ProtoFieldExpected(&'static str),
44
45    #[error("IO error of kind {0}")]
46    Io(#[from] std::io::Error),
47
48    #[error("Error from remote store: {0}")]
49    Remote(String),
50
51    #[error("Timeout error: {0:?} > {0:?}")]
52    Timeout(Duration, Duration),
53
54    // Remote has dropped watched query. Error message needs to be synchronized
55    // with `client.rs` message handling for re-register handling.
56    #[error("Watched query got unregistered")]
57    WatchedUnregistered,
58
59    #[error("Not connected to any store node")]
60    NotConnected,
61
62    #[error("Try to lock a mutex that was poisoned")]
63    Poisoned,
64
65    #[error("Query or mutation got cancelled")]
66    Cancelled,
67
68    #[error("Dropped or couldn't get locked")]
69    Dropped,
70
71    #[error("A fatal error occurred: {0}")]
72    Fatal(#[source] anyhow::Error),
73
74    #[error(transparent)]
75    Other(#[from] anyhow::Error),
76}
77
78impl Error {
79    pub fn is_fatal(&self) -> bool {
80        #![allow(clippy::match_like_matches_macro)]
81        match self {
82            Error::Fatal(_) | Error::Poisoned | Error::Dropped | Error::Io(_) => true,
83
84            #[cfg(feature = "local")]
85            Error::TantivyOpenDirectoryError(_) => true,
86
87            #[cfg(feature = "local")]
88            Error::ChainEngine(err) if err.is_fatal() => true,
89
90            _ => false,
91        }
92    }
93}
94
95impl From<exocore_protos::prost::DecodeError> for Error {
96    fn from(err: exocore_protos::prost::DecodeError) -> Self {
97        Error::Proto(err.into())
98    }
99}
100
101impl From<exocore_protos::prost::EncodeError> for Error {
102    fn from(err: exocore_protos::prost::EncodeError) -> Self {
103        Error::Proto(err.into())
104    }
105}
106
107impl<T> From<std::sync::PoisonError<T>> for Error {
108    fn from(_err: std::sync::PoisonError<T>) -> Self {
109        Error::Poisoned
110    }
111}