zescrow_core/
error.rs

1use thiserror::Error;
2
3use crate::BigNumber;
4
5/// Errors arising from on-chain `Escrow` operations and parameter validation.
6#[derive(Debug, Error)]
7pub enum EscrowError {
8    /// A cryptographic condition failed to verify.
9    #[error("condition error: {0}")]
10    Condition(#[from] ConditionError),
11
12    /// Attempted to transition an `Escrow` in an invalid state.
13    #[error("invalid state transition")]
14    InvalidState,
15
16    /// An identity could not be parsed or validated.
17    #[error("identity error: {0}")]
18    Identity(#[from] IdentityError),
19
20    /// An asset failed parsing, validation, or formatting.
21    #[error("asset error: {0}")]
22    Asset(#[from] AssetError),
23
24    /// Attempted a chain-specific operation on the wrong network
25    /// (e.g., getting Solana PDA on Ethereum).
26    #[error("invalid chain operation: {0}")]
27    InvalidChainOp(String),
28
29    /// An I/O error occurred (e.g., reading or writing JSON files).
30    #[error("I/O error: {0}")]
31    Io(#[from] std::io::Error),
32
33    /// JSON parsing or serialization error.
34    #[cfg(feature = "json")]
35    #[error("JSON error: {0}")]
36    Json(#[from] serde_json::Error),
37
38    /// The specified blockchain network is not supported.
39    #[error("unsupported chain specified")]
40    UnsupportedChain,
41}
42
43/// Errors related to cryptographic condition verification.
44#[derive(Debug, Error)]
45pub enum ConditionError {
46    /// Hashlock error
47    #[error("preimage (hashlock) failed: {0}")]
48    Hashlock(#[from] crate::condition::hashlock::Error),
49
50    /// Ed25519 error
51    #[error("ed25519 signature failed: {0}")]
52    Ed25519(#[from] crate::condition::ed25519::Error),
53
54    /// Secp256k1 error
55    #[error("secp256k1 signature failed: {0}")]
56    Secp256k1(#[from] crate::condition::secp256k1::Error),
57
58    /// Threshold error
59    #[error("threshold check failed: {0}")]
60    Threshold(#[from] crate::condition::threshold::Error),
61}
62
63/// Errors related to identity parsing and validation.
64#[derive(Debug, Error)]
65pub enum IdentityError {
66    /// The provided identity string was empty.
67    #[error("empty identity string")]
68    EmptyIdentity,
69
70    /// The provided identity string exceeds the maximum allowed.
71    #[error("input length {len} exceeds maximum of {max} characters")]
72    InputTooLong {
73        /// Input length
74        len: usize,
75        /// Max allowed
76        max: usize,
77    },
78
79    /// Error decoding a hex-encoded identity.
80    #[error("hex decoding error: {0}")]
81    Hex(#[from] hex::FromHexError),
82
83    /// Error decoding a Base58-encoded identity.
84    #[error("Base58 decoding error: {0}")]
85    Base58(#[from] bs58::decode::Error),
86
87    /// Error decoding a Base64-encoded identity.
88    #[error("Base64 decoding error: {0}")]
89    Base64(#[from] base64::DecodeError),
90
91    /// The input string did not match any supported identity format (hex, Base58, Base64).
92    #[error("unsupported identity format")]
93    UnsupportedFormat,
94}
95
96/// Errors related to asset parsing, validation, or formatting.
97#[derive(Debug, Error)]
98pub enum AssetError {
99    /// Failed to parse an asset from a string or JSON.
100    #[error("could not serialize asset: {0}")]
101    Serialization(String),
102
103    /// Failed to parse an asset from bytes or JSON.
104    #[error("could not parse asset: {0}")]
105    Parsing(String),
106
107    /// A fungible or multi-token amount and/or total supply was zero, which is not allowed.
108    #[error("amount must be non-zero")]
109    ZeroAmount,
110
111    /// ID for asset, program, or contract not provided.
112    #[error("missing ID for asset, program, or contract")]
113    MissingId,
114
115    /// Total supply of token not provided.
116    #[error("missing `total_supply` for specified token")]
117    MissingTotalSupply,
118
119    /// Invalid ID for asset, program, or contract.
120    #[error("inalid ID for asset, program, or contract")]
121    InvalidId,
122
123    /// A liquidity pool share was invalid;
124    /// `share` must be > 0 and <= total supply.
125    #[error("share must be non-zero and <= total supply (share={0}, total={1})")]
126    InvalidShare(BigNumber, BigNumber),
127
128    /// The specified number of decimals was invalid.
129    #[error("invalid decimals: {0}")]
130    InvalidDecimals(u8),
131
132    /// Fixed-point formatting overflow (e.g., amount or decimals too large).
133    #[error("human formatting overflow: amount={0}, decimals={1}")]
134    FormatOverflow(BigNumber, u8),
135
136    /// The provided asset string did not match a supported format.
137    #[error("unsupported asset string format")]
138    UnsupportedFormat,
139
140    /// Error parsing an integer (e.g., token ID or amount) from a string.
141    #[error("integer parsing error: {0}")]
142    ParseInt(#[from] std::num::ParseIntError),
143}
144
145impl EscrowError {
146    /// A helper to bypass the unavailability of the `ToString` trait
147    /// in the RISC Zero guest.
148    pub fn to_str(&self) -> String {
149        self.to_string()
150    }
151}