eth_twc_sdk/
error.rs

1//! [`SdkError`] — SDK 各 API で返りうるエラー。
2
3use alloy::primitives::{Address, U256};
4use thiserror::Error;
5
6/// SDK 全体で返すエラー型(RPC・コントラクト・署名・検証の失敗をまとめる)。
7#[derive(Debug, Error)]
8pub enum SdkError {
9    /// [`crate::config::transfer_with_commitment_address`] がゼロアドレスのまま API を呼んだ。
10    #[error(
11        "transferWithCommitmentAddress is not configured (zero address). Set ETH_TWC_CONTRACT_ADDRESS for integration-test, or use default release build with CREATE2 address baked in config."
12    )]
13    ContractNotConfigured,
14
15    /// 期待する TWC アドレスにコントラクトコードが無い。
16    #[error(
17        "TransferWithCommitment is not deployed at {address} on chain id {chain_id} (no contract code). Deploy via CREATE2 (see contracts/TWC_CREATE2.md)."
18    )]
19    ContractNotDeployed { address: Address, chain_id: u64 },
20
21    /// 署名済みデータの `domain.chainId` が RPC のチェーン ID と一致しない。
22    #[error(
23        "Signed data domain.chain_id ({domain}) does not match client chain id ({client})"
24    )]
25    DomainChainIdMismatch { domain: String, client: u64 },
26
27    /// 署名済みデータの `domain.verifyingContract` が設定アドレスと一致しない。
28    #[error(
29        "Signed data domain.verifyingContract ({domain}) does not match transferWithCommitmentAddress ({configured})"
30    )]
31    DomainVerifyingContractMismatch {
32        domain: Address,
33        configured: Address,
34    },
35
36    /// EIP-712 メッセージの `validAfter` が `validBefore` より大きい(有効期間が空)。
37    #[error(
38        "validAfter ({valid_after}) must be <= validBefore ({valid_before})"
39    )]
40    InvalidValidTimeWindow {
41        valid_after: U256,
42        valid_before: U256,
43    },
44
45    /// [`crate::sign::uni_commit_transfers`] / [`crate::sign::batch_transfer_with_commit`]、および [`crate::send_transaction::self_transfer::unified_transfer`] / [`crate::send_transaction::self_transfer::batch_transfer`] で明細配列が空(コントラクトは revert する)。
46    #[error("transfer details must not be empty")]
47    EmptyTransferDetails,
48
49    /// EIP-712 メッセージの `from` が [`Signer::address`](alloy::signers::Signer::address) と一致しない(オンチェーン検証で署名が通らないため、署名前に拒否する)。
50    #[error(
51        "EIP-712 message `from` ({from}) does not match signer address ({signer})"
52    )]
53    FromSignerMismatch { from: Address, signer: Address },
54
55    /// `CancelAuthorization` の `authorizer` が [`Signer::address`](alloy::signers::Signer::address) と一致しない。
56    #[error(
57        "CancelAuthorization `authorizer` ({authorizer}) does not match signer address ({signer})"
58    )]
59    AuthorizerSignerMismatch { authorizer: Address, signer: Address },
60
61    /// [`crate::verify::verify`] で、条件に合致する `TransferWithCommitmentSent` ログが 1 件もなかった。
62    #[error("TransferWithCommitmentSent event not found")]
63    EventNotFound,
64
65    /// 指定ハッシュのトランザクションレシートが RPC から返らなかった([`crate::verify::verify`]・[`crate::verify::get_transfer_with_commitment_sent_event_logs`])。
66    #[error("Transaction receipt not found for the given hash")]
67    ReceiptNotFound,
68
69    /// RPC 呼び出しまたはコントラクトエンコード/デコードの失敗。
70    #[error("RPC / contract error: {0}")]
71    Alloy(String),
72
73    /// [`alloy::signers::Signer`] によるハッシュ署名の失敗。
74    #[error("Signing error: {0}")]
75    Signer(#[from] alloy::signers::Error),
76}
77
78impl From<alloy::contract::Error> for SdkError {
79    fn from(e: alloy::contract::Error) -> Self {
80        SdkError::Alloy(e.to_string())
81    }
82}
83
84impl From<alloy::transports::TransportError> for SdkError {
85    fn from(e: alloy::transports::TransportError) -> Self {
86        SdkError::Alloy(e.to_string())
87    }
88}