use crate::{ChainId, MessageId, StateKey};
use thiserror::Error;
#[derive(Clone, Debug, Error)]
pub enum XenithError {
#[error("transport error on chain {chain}: {message}")]
Transport { chain: ChainId, message: String },
#[error("state diverged for key {key} across chains: {chains:?}")]
Divergence { key: StateKey, chains: Vec<ChainId> },
#[error("message {id} timed out after {elapsed_secs}s")]
Timeout { id: MessageId, elapsed_secs: u64 },
#[error("insufficient fee: required {required}, provided {provided}")]
InsufficientFee { required: String, provided: String },
#[error("chain {0} is not supported by this transport")]
UnsupportedChain(ChainId),
#[error("state store error: {0}")]
StoreError(String),
#[error("serialization error: {0}")]
Serialization(String),
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn transport_message() {
let e = XenithError::Transport {
chain: ChainId(1),
message: "connection refused".into(),
};
assert_eq!(
e.to_string(),
"transport error on chain 1: connection refused"
);
}
#[test]
fn divergence_message() {
let e = XenithError::Divergence {
key: StateKey::new("proto", "pool", "0xabc"),
chains: vec![ChainId(1), ChainId(42161)],
};
assert_eq!(
e.to_string(),
"state diverged for key proto.pool.0xabc across chains: [ChainId(1), ChainId(42161)]"
);
}
#[test]
fn timeout_message() {
let e = XenithError::Timeout {
id: MessageId(7),
elapsed_secs: 30,
};
assert_eq!(e.to_string(), "message 7 timed out after 30s");
}
#[test]
fn insufficient_fee_message() {
let e = XenithError::InsufficientFee {
required: "500000".into(),
provided: "100000".into(),
};
assert_eq!(
e.to_string(),
"insufficient fee: required 500000, provided 100000"
);
}
#[test]
fn unsupported_chain_message() {
let e = XenithError::UnsupportedChain(ChainId(9999));
assert_eq!(
e.to_string(),
"chain 9999 is not supported by this transport"
);
}
#[test]
fn store_error_message() {
let e = XenithError::StoreError("disk full".into());
assert_eq!(e.to_string(), "state store error: disk full");
}
#[test]
fn serialization_message() {
let e = XenithError::Serialization("unexpected EOF".into());
assert_eq!(e.to_string(), "serialization error: unexpected EOF");
}
#[test]
fn implements_std_error() {
fn takes_error(_: &dyn std::error::Error) {}
takes_error(&XenithError::StoreError("x".into()));
}
}