1use std::fmt::{self, Debug, Formatter};
4use std::future::Future;
5use std::pin::Pin;
6
7use compact_str::CompactString;
8use r402_protocol::{ChainId, ClientError, PaymentRequired, PaymentRequirements, SchemeId};
9
10#[derive(Debug, Clone, PartialEq, Eq)]
12pub struct DefaultAssetInfo {
13 pub asset: CompactString,
15 pub decimals: u32,
17 pub symbol: CompactString,
19 pub asset_transfer_method: Option<CompactString>,
21}
22
23impl DefaultAssetInfo {
24 #[must_use]
26 pub fn new(
27 asset: impl Into<CompactString>,
28 decimals: u32,
29 symbol: impl Into<CompactString>,
30 ) -> Self {
31 Self {
32 asset: asset.into(),
33 decimals,
34 symbol: symbol.into(),
35 asset_transfer_method: None,
36 }
37 }
38
39 #[must_use]
41 pub fn with_asset_transfer_method(mut self, method: impl Into<CompactString>) -> Self {
42 self.asset_transfer_method = Some(method.into());
43 self
44 }
45}
46
47pub trait SchemeClient: SchemeId + Send + Sync {
49 fn accept(&self, payment_required: &PaymentRequired) -> Vec<PaymentCandidate>;
51
52 fn find_default_asset(&self, asset: &str, network: &ChainId) -> Option<DefaultAssetInfo>;
54}
55
56pub struct PaymentCandidate {
58 pub chain_id: ChainId,
60 pub asset: CompactString,
62 pub amount: CompactString,
64 pub scheme: CompactString,
66 pub pay_to: CompactString,
68 pub requirements: PaymentRequirements,
70 pub signer: Box<dyn PaymentCandidateSigner>,
72}
73
74impl Debug for PaymentCandidate {
75 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
76 f.debug_struct("PaymentCandidate")
77 .field("chain_id", &self.chain_id)
78 .field("asset", &self.asset)
79 .field("amount", &self.amount)
80 .field("scheme", &self.scheme)
81 .field("pay_to", &self.pay_to)
82 .finish_non_exhaustive()
83 }
84}
85
86impl PaymentCandidate {
87 pub async fn sign(&self) -> Result<String, ClientError> {
93 self.signer.sign_payment().await
94 }
95}
96
97pub trait PaymentCandidateSigner: Send + Sync {
99 fn sign_payment<'a>(
101 &'a self,
102 ) -> Pin<Box<dyn Future<Output = Result<String, ClientError>> + Send + 'a>>;
103}