1#![allow(unexpected_cfgs)]
17
18use std::fmt;
19
20use crate::util::*;
21use monero::{cryptonote::hash::Hash as CryptoNoteHash, util::address::PaymentId};
22use serde::{
23 Deserialize, Deserializer, Serialize,
24 de::{Error as DeserializerError, Visitor},
25};
26
27macro_rules! hash_type {
28 ($name:ident, $len:expr) => {
29 ::fixed_hash::construct_fixed_hash! {
30 #[derive(::serde::Serialize, ::serde::Deserialize)]
31 pub struct $name($len);
32 }
33 hash_type_impl!($name);
34 };
35}
36
37hash_type!(BlockHash, 32);
38
39#[derive(Clone, Debug, Serialize, Deserialize)]
40pub enum Status {
41 OK,
42}
43
44#[derive(Clone, Debug, Serialize, Deserialize)]
45#[serde(tag = "status")]
46pub enum MoneroResult<T> {
47 OK(T),
48}
49
50impl<T> MoneroResult<T> {
51 pub fn into_inner(self) -> T {
52 match self {
53 MoneroResult::OK(v) => v,
54 }
55 }
56}
57
58fn number_or_boolean<'de, D>(deserializer: D) -> Result<bool, D::Error>
60where
61 D: Deserializer<'de>,
62{
63 struct BoolVisitor;
64
65 impl<'de> Visitor<'de> for BoolVisitor {
66 type Value = bool;
67
68 fn expecting(&self, formatter: &mut fmt::Formatter) -> fmt::Result {
69 formatter.write_str("integer or boolean")
70 }
71
72 fn visit_bool<E: DeserializerError>(self, value: bool) -> Result<bool, E> {
73 Ok(value)
74 }
75
76 fn visit_u64<E: DeserializerError>(self, value: u64) -> Result<bool, E> {
77 let boolean = match value {
78 0 => false,
79 1 => true,
80 _ => {
81 return Err(E::invalid_value(
82 serde::de::Unexpected::Unsigned(value),
83 &self,
84 ));
85 }
86 };
87 Ok(boolean)
88 }
89 }
90
91 deserializer.deserialize_any(BoolVisitor)
92}
93
94#[derive(Clone, Debug, Serialize, Deserialize)]
95pub struct AddressInfo {
96 pub locked_funds: String,
97 pub total_received: String,
98 pub total_sent: String,
99 pub scanned_height: u64,
100 pub scanned_block_height: u64,
101 pub start_height: u64,
102 pub transaction_height: u64,
103 pub blockchain_height: u64,
104 pub spent_outputs: Vec<SpendObject>,
105 pub rates: Option<Rates>,
106}
107
108#[derive(Clone, Debug, Serialize, Deserialize)]
109#[allow(non_snake_case)]
110pub struct Rates {
111 pub AUD: Option<f32>,
112}
113
114#[derive(Clone, Debug, Serialize, Deserialize)]
115pub struct SpendObject {
116 pub amount: String,
117 pub key_image: HashString<CryptoNoteHash>,
118 pub tx_pub_key: HashString<CryptoNoteHash>,
119 pub out_index: u16,
120 pub mixin: u32,
121}
122
123#[derive(Clone, Debug, Serialize, Deserialize)]
124pub struct AddressTxs {
125 pub total_received: String,
126 pub scanned_height: u64,
127 pub scanned_block_height: u64,
128 pub start_height: u64,
129 pub blockchain_height: u64,
130 #[serde(default)]
132 pub transactions: Vec<Transaction>,
133}
134
135#[derive(Clone, Debug, Serialize, Deserialize)]
136pub struct Transaction {
137 pub id: u64,
138 pub hash: HashString<CryptoNoteHash>,
139 pub timestamp: String,
140 pub total_received: String,
141 pub total_sent: String,
142 pub unlock_time: u64,
143 pub height: Option<u64>,
144 #[serde(default)]
146 pub spent_outputs: Vec<SpendObject>,
147 pub payment_id: Option<HashString<PaymentId>>,
148 #[serde(deserialize_with = "number_or_boolean")]
149 pub coinbase: bool,
150 #[serde(deserialize_with = "number_or_boolean")]
151 pub mempool: bool,
152 pub mixin: u32,
153}
154
155#[derive(Clone, Debug, Serialize, Deserialize)]
156pub struct AmountOuts {
157 pub amount_outs: Vec<RandomOutput>,
158}
159
160#[derive(Clone, Debug, Serialize, Deserialize)]
161pub struct RandomOutputs {
162 pub amount: String,
163 pub outputs: Vec<RandomOutput>,
164}
165
166#[derive(Clone, Debug, Serialize, Deserialize)]
167pub struct RandomOutput {
168 pub global_index: u64,
169 pub public_key: HashString<CryptoNoteHash>,
170 pub rct: HashString<CryptoNoteHash>,
171}
172
173#[derive(Clone, Debug, Serialize, Deserialize)]
174pub struct UnspentOuts {
175 pub per_kb_fee: u64,
176 pub fee_mask: u64,
177 pub amount: String,
178 pub outputs: Vec<Output>,
179}
180
181#[derive(Clone, Debug, Serialize, Deserialize)]
182pub struct Output {
183 pub tx_id: u64,
184 pub amount: String,
185 pub index: u16,
186 pub global_index: u64,
187 pub rct: String,
188 pub tx_hash: HashString<CryptoNoteHash>,
189 pub tx_prefix_hash: String,
190 pub public_key: HashString<CryptoNoteHash>,
191 pub tx_pub_key: HashString<CryptoNoteHash>,
192 pub spend_key_images: Vec<HashString<CryptoNoteHash>>,
193 pub timestamp: String,
194 pub height: u64,
195}
196
197#[derive(Clone, Debug, Serialize, Deserialize)]
198pub struct ImportResponse {
199 pub payment_address: Option<monero::Address>,
200 pub payment_id: Option<HashString<PaymentId>>,
201 pub import_fee: Option<String>,
202 #[serde(deserialize_with = "number_or_boolean")]
203 pub new_request: bool,
204 #[serde(deserialize_with = "number_or_boolean")]
205 pub request_fulfilled: bool,
206 pub status: String,
207}
208
209#[derive(Clone, Debug, Serialize, Deserialize)]
210pub struct LoginResponse {
211 #[serde(deserialize_with = "number_or_boolean")]
212 pub new_address: bool,
213 #[serde(deserialize_with = "number_or_boolean")]
214 pub generated_locally: bool,
215 pub start_height: Option<u64>,
216}