1#![allow(non_snake_case)]
2
3use std::convert::Infallible;
4use std::io;
5
6use actix::MailboxError;
7use anyhow::anyhow;
8use futures::channel::oneshot::Canceled;
9use serde::{Deserialize, Serialize};
10use serde_with::{serde_as, serde_conv};
11use solana_message::CompileError;
12use solana_program::clock::Slot;
13use solana_pubkey::Pubkey;
14use solana_rpc_client_api::client_error::{Error as ClientError, ErrorKind as ClientErrorKind};
15use solana_rpc_client_api::request::{RpcError, RpcRequest, RpcResponseErrorData};
16use solana_rpc_client_api::response::RpcSimulateTransactionResult;
17use solana_sanitize::SanitizeError;
18use solana_signer::{PresignerError, SignerError};
19use solana_transaction_error::TransactionError;
20
21#[derive(Serialize, Deserialize)]
22pub enum AsRpcRequestImpl {
23 Custom,
24 DeregisterNode,
25 GetAccountInfo,
26 GetBalance,
27 GetBlock,
28 GetBlockHeight,
29 GetBlockProduction,
30 GetBlocks,
31 GetBlocksWithLimit,
32 GetBlockTime,
33 GetClusterNodes,
34 GetEpochInfo,
35 GetEpochSchedule,
36 GetFeeForMessage,
37 GetFirstAvailableBlock,
38 GetGenesisHash,
39 GetHealth,
40 GetIdentity,
41 GetInflationGovernor,
42 GetInflationRate,
43 GetInflationReward,
44 GetLargestAccounts,
45 GetLatestBlockhash,
46 GetLeaderSchedule,
47 GetMaxRetransmitSlot,
48 GetMaxShredInsertSlot,
49 GetMinimumBalanceForRentExemption,
50 GetMultipleAccounts,
51 GetProgramAccounts,
52 GetRecentPerformanceSamples,
53 GetRecentPrioritizationFees,
54 GetHighestSnapshotSlot,
55 GetSignaturesForAddress,
56 GetSignatureStatuses,
57 GetSlot,
58 GetSlotLeader,
59 GetSlotLeaders,
60 GetStorageTurn,
61 GetStorageTurnRate,
62 GetSlotsPerSegment,
63 GetStakeMinimumDelegation,
64 GetStoragePubkeysForSlot,
65 GetSupply,
66 GetTokenAccountBalance,
67 GetTokenAccountsByDelegate,
68 GetTokenAccountsByOwner,
69 GetTokenLargestAccounts,
70 GetTokenSupply,
71 GetTransaction,
72 GetTransactionCount,
73 GetVersion,
74 GetVoteAccounts,
75 IsBlockhashValid,
76 MinimumLedgerSlot,
77 RegisterNode,
78 RequestAirdrop,
79 SendTransaction,
80 SimulateTransaction,
81 SignVote,
82}
83
84fn ser_rpc_request(r: &RpcRequest) -> AsRpcRequestImpl {
85 match r {
86 RpcRequest::Custom { .. } => AsRpcRequestImpl::Custom,
87 RpcRequest::DeregisterNode => AsRpcRequestImpl::DeregisterNode,
88 RpcRequest::GetAccountInfo => AsRpcRequestImpl::GetAccountInfo,
89 RpcRequest::GetBalance => AsRpcRequestImpl::GetBalance,
90 RpcRequest::GetBlock => AsRpcRequestImpl::GetBlock,
91 RpcRequest::GetBlockHeight => AsRpcRequestImpl::GetBlockHeight,
92 RpcRequest::GetBlockProduction => AsRpcRequestImpl::GetBlockProduction,
93 RpcRequest::GetBlocks => AsRpcRequestImpl::GetBlocks,
94 RpcRequest::GetBlocksWithLimit => AsRpcRequestImpl::GetBlocksWithLimit,
95 RpcRequest::GetBlockTime => AsRpcRequestImpl::GetBlockTime,
96 RpcRequest::GetClusterNodes => AsRpcRequestImpl::GetClusterNodes,
97 RpcRequest::GetEpochInfo => AsRpcRequestImpl::GetEpochInfo,
98 RpcRequest::GetEpochSchedule => AsRpcRequestImpl::GetEpochSchedule,
99 RpcRequest::GetFeeForMessage => AsRpcRequestImpl::GetFeeForMessage,
100 RpcRequest::GetFirstAvailableBlock => AsRpcRequestImpl::GetFirstAvailableBlock,
101 RpcRequest::GetGenesisHash => AsRpcRequestImpl::GetGenesisHash,
102 RpcRequest::GetHealth => AsRpcRequestImpl::GetHealth,
103 RpcRequest::GetIdentity => AsRpcRequestImpl::GetIdentity,
104 RpcRequest::GetInflationGovernor => AsRpcRequestImpl::GetInflationGovernor,
105 RpcRequest::GetInflationRate => AsRpcRequestImpl::GetInflationRate,
106 RpcRequest::GetInflationReward => AsRpcRequestImpl::GetInflationReward,
107 RpcRequest::GetLargestAccounts => AsRpcRequestImpl::GetLargestAccounts,
108 RpcRequest::GetLatestBlockhash => AsRpcRequestImpl::GetLatestBlockhash,
109 RpcRequest::GetLeaderSchedule => AsRpcRequestImpl::GetLeaderSchedule,
110 RpcRequest::GetMaxRetransmitSlot => AsRpcRequestImpl::GetMaxRetransmitSlot,
111 RpcRequest::GetMaxShredInsertSlot => AsRpcRequestImpl::GetMaxShredInsertSlot,
112 RpcRequest::GetMinimumBalanceForRentExemption => {
113 AsRpcRequestImpl::GetMinimumBalanceForRentExemption
114 }
115 RpcRequest::GetMultipleAccounts => AsRpcRequestImpl::GetMultipleAccounts,
116 RpcRequest::GetProgramAccounts => AsRpcRequestImpl::GetProgramAccounts,
117 RpcRequest::GetRecentPerformanceSamples => AsRpcRequestImpl::GetRecentPerformanceSamples,
118 RpcRequest::GetRecentPrioritizationFees => AsRpcRequestImpl::GetRecentPrioritizationFees,
119 RpcRequest::GetHighestSnapshotSlot => AsRpcRequestImpl::GetHighestSnapshotSlot,
120 RpcRequest::GetSignaturesForAddress => AsRpcRequestImpl::GetSignaturesForAddress,
121 RpcRequest::GetSignatureStatuses => AsRpcRequestImpl::GetSignatureStatuses,
122 RpcRequest::GetSlot => AsRpcRequestImpl::GetSlot,
123 RpcRequest::GetSlotLeader => AsRpcRequestImpl::GetSlotLeader,
124 RpcRequest::GetSlotLeaders => AsRpcRequestImpl::GetSlotLeaders,
125 RpcRequest::GetStorageTurn => AsRpcRequestImpl::GetStorageTurn,
126 RpcRequest::GetStorageTurnRate => AsRpcRequestImpl::GetStorageTurnRate,
127 RpcRequest::GetSlotsPerSegment => AsRpcRequestImpl::GetSlotsPerSegment,
128 RpcRequest::GetStakeMinimumDelegation => AsRpcRequestImpl::GetStakeMinimumDelegation,
129 RpcRequest::GetStoragePubkeysForSlot => AsRpcRequestImpl::GetStoragePubkeysForSlot,
130 RpcRequest::GetSupply => AsRpcRequestImpl::GetSupply,
131 RpcRequest::GetTokenAccountBalance => AsRpcRequestImpl::GetTokenAccountBalance,
132 RpcRequest::GetTokenAccountsByDelegate => AsRpcRequestImpl::GetTokenAccountsByDelegate,
133 RpcRequest::GetTokenAccountsByOwner => AsRpcRequestImpl::GetTokenAccountsByOwner,
134 RpcRequest::GetTokenLargestAccounts => AsRpcRequestImpl::GetTokenLargestAccounts,
135 RpcRequest::GetTokenSupply => AsRpcRequestImpl::GetTokenSupply,
136 RpcRequest::GetTransaction => AsRpcRequestImpl::GetTransaction,
137 RpcRequest::GetTransactionCount => AsRpcRequestImpl::GetTransactionCount,
138 RpcRequest::GetVersion => AsRpcRequestImpl::GetVersion,
139 RpcRequest::GetVoteAccounts => AsRpcRequestImpl::GetVoteAccounts,
140 RpcRequest::IsBlockhashValid => AsRpcRequestImpl::IsBlockhashValid,
141 RpcRequest::MinimumLedgerSlot => AsRpcRequestImpl::MinimumLedgerSlot,
142 RpcRequest::RegisterNode => AsRpcRequestImpl::RegisterNode,
143 RpcRequest::RequestAirdrop => AsRpcRequestImpl::RequestAirdrop,
144 RpcRequest::SendTransaction => AsRpcRequestImpl::SendTransaction,
145 RpcRequest::SimulateTransaction => AsRpcRequestImpl::SimulateTransaction,
146 RpcRequest::SignVote => AsRpcRequestImpl::SignVote,
147 }
148}
149
150fn de_rpc_request(r: AsRpcRequestImpl) -> Result<RpcRequest, Infallible> {
151 Ok(match r {
152 AsRpcRequestImpl::Custom => RpcRequest::Custom { method: "unknown" },
153 AsRpcRequestImpl::DeregisterNode => RpcRequest::DeregisterNode,
154 AsRpcRequestImpl::GetAccountInfo => RpcRequest::GetAccountInfo,
155 AsRpcRequestImpl::GetBalance => RpcRequest::GetBalance,
156 AsRpcRequestImpl::GetBlock => RpcRequest::GetBlock,
157 AsRpcRequestImpl::GetBlockHeight => RpcRequest::GetBlockHeight,
158 AsRpcRequestImpl::GetBlockProduction => RpcRequest::GetBlockProduction,
159 AsRpcRequestImpl::GetBlocks => RpcRequest::GetBlocks,
160 AsRpcRequestImpl::GetBlocksWithLimit => RpcRequest::GetBlocksWithLimit,
161 AsRpcRequestImpl::GetBlockTime => RpcRequest::GetBlockTime,
162 AsRpcRequestImpl::GetClusterNodes => RpcRequest::GetClusterNodes,
163 AsRpcRequestImpl::GetEpochInfo => RpcRequest::GetEpochInfo,
164 AsRpcRequestImpl::GetEpochSchedule => RpcRequest::GetEpochSchedule,
165 AsRpcRequestImpl::GetFeeForMessage => RpcRequest::GetFeeForMessage,
166 AsRpcRequestImpl::GetFirstAvailableBlock => RpcRequest::GetFirstAvailableBlock,
167 AsRpcRequestImpl::GetGenesisHash => RpcRequest::GetGenesisHash,
168 AsRpcRequestImpl::GetHealth => RpcRequest::GetHealth,
169 AsRpcRequestImpl::GetIdentity => RpcRequest::GetIdentity,
170 AsRpcRequestImpl::GetInflationGovernor => RpcRequest::GetInflationGovernor,
171 AsRpcRequestImpl::GetInflationRate => RpcRequest::GetInflationRate,
172 AsRpcRequestImpl::GetInflationReward => RpcRequest::GetInflationReward,
173 AsRpcRequestImpl::GetLargestAccounts => RpcRequest::GetLargestAccounts,
174 AsRpcRequestImpl::GetLatestBlockhash => RpcRequest::GetLatestBlockhash,
175 AsRpcRequestImpl::GetLeaderSchedule => RpcRequest::GetLeaderSchedule,
176 AsRpcRequestImpl::GetMaxRetransmitSlot => RpcRequest::GetMaxRetransmitSlot,
177 AsRpcRequestImpl::GetMaxShredInsertSlot => RpcRequest::GetMaxShredInsertSlot,
178 AsRpcRequestImpl::GetMinimumBalanceForRentExemption => {
179 RpcRequest::GetMinimumBalanceForRentExemption
180 }
181 AsRpcRequestImpl::GetMultipleAccounts => RpcRequest::GetMultipleAccounts,
182 AsRpcRequestImpl::GetProgramAccounts => RpcRequest::GetProgramAccounts,
183 AsRpcRequestImpl::GetRecentPerformanceSamples => RpcRequest::GetRecentPerformanceSamples,
184 AsRpcRequestImpl::GetRecentPrioritizationFees => RpcRequest::GetRecentPrioritizationFees,
185 AsRpcRequestImpl::GetHighestSnapshotSlot => RpcRequest::GetHighestSnapshotSlot,
186 AsRpcRequestImpl::GetSignaturesForAddress => RpcRequest::GetSignaturesForAddress,
187 AsRpcRequestImpl::GetSignatureStatuses => RpcRequest::GetSignatureStatuses,
188 AsRpcRequestImpl::GetSlot => RpcRequest::GetSlot,
189 AsRpcRequestImpl::GetSlotLeader => RpcRequest::GetSlotLeader,
190 AsRpcRequestImpl::GetSlotLeaders => RpcRequest::GetSlotLeaders,
191 AsRpcRequestImpl::GetStorageTurn => RpcRequest::GetStorageTurn,
192 AsRpcRequestImpl::GetStorageTurnRate => RpcRequest::GetStorageTurnRate,
193 AsRpcRequestImpl::GetSlotsPerSegment => RpcRequest::GetSlotsPerSegment,
194 AsRpcRequestImpl::GetStakeMinimumDelegation => RpcRequest::GetStakeMinimumDelegation,
195 AsRpcRequestImpl::GetStoragePubkeysForSlot => RpcRequest::GetStoragePubkeysForSlot,
196 AsRpcRequestImpl::GetSupply => RpcRequest::GetSupply,
197 AsRpcRequestImpl::GetTokenAccountBalance => RpcRequest::GetTokenAccountBalance,
198 AsRpcRequestImpl::GetTokenAccountsByDelegate => RpcRequest::GetTokenAccountsByDelegate,
199 AsRpcRequestImpl::GetTokenAccountsByOwner => RpcRequest::GetTokenAccountsByOwner,
200 AsRpcRequestImpl::GetTokenLargestAccounts => RpcRequest::GetTokenLargestAccounts,
201 AsRpcRequestImpl::GetTokenSupply => RpcRequest::GetTokenSupply,
202 AsRpcRequestImpl::GetTransaction => RpcRequest::GetTransaction,
203 AsRpcRequestImpl::GetTransactionCount => RpcRequest::GetTransactionCount,
204 AsRpcRequestImpl::GetVersion => RpcRequest::GetVersion,
205 AsRpcRequestImpl::GetVoteAccounts => RpcRequest::GetVoteAccounts,
206 AsRpcRequestImpl::IsBlockhashValid => RpcRequest::IsBlockhashValid,
207 AsRpcRequestImpl::MinimumLedgerSlot => RpcRequest::MinimumLedgerSlot,
208 AsRpcRequestImpl::RegisterNode => RpcRequest::RegisterNode,
209 AsRpcRequestImpl::RequestAirdrop => RpcRequest::RequestAirdrop,
210 AsRpcRequestImpl::SendTransaction => RpcRequest::SendTransaction,
211 AsRpcRequestImpl::SimulateTransaction => RpcRequest::SimulateTransaction,
212 AsRpcRequestImpl::SignVote => RpcRequest::SignVote,
213 })
214}
215
216serde_conv!(pub AsRpcRequest, RpcRequest, ser_rpc_request, de_rpc_request);
217
218#[derive(Serialize, Deserialize)]
219pub enum AsRpcResponseErrorDataImpl {
220 Empty,
221 SendTransactionPreflightFailure(Box<RpcSimulateTransactionResult>),
222 NodeUnhealthy { num_slots_behind: Option<Slot> },
223}
224
225fn ser_rpc_response_error_data(error: &RpcResponseErrorData) -> AsRpcResponseErrorDataImpl {
226 match error {
227 RpcResponseErrorData::Empty => AsRpcResponseErrorDataImpl::Empty,
228 RpcResponseErrorData::SendTransactionPreflightFailure(rpc_simulate_transaction_result) => {
229 AsRpcResponseErrorDataImpl::SendTransactionPreflightFailure(Box::new(
230 rpc_simulate_transaction_result.clone(),
231 ))
232 }
233 RpcResponseErrorData::NodeUnhealthy { num_slots_behind } => {
234 AsRpcResponseErrorDataImpl::NodeUnhealthy {
235 num_slots_behind: *num_slots_behind,
236 }
237 }
238 }
239}
240
241fn de_rpc_response_error_data(
242 error: AsRpcResponseErrorDataImpl,
243) -> Result<RpcResponseErrorData, Infallible> {
244 Ok(match error {
245 AsRpcResponseErrorDataImpl::Empty => RpcResponseErrorData::Empty,
246 AsRpcResponseErrorDataImpl::SendTransactionPreflightFailure(
247 rpc_simulate_transaction_result,
248 ) => {
249 RpcResponseErrorData::SendTransactionPreflightFailure(*rpc_simulate_transaction_result)
250 }
251 AsRpcResponseErrorDataImpl::NodeUnhealthy { num_slots_behind } => {
252 RpcResponseErrorData::NodeUnhealthy { num_slots_behind }
253 }
254 })
255}
256
257serde_conv!(pub AsRpcResponseErrorData, RpcResponseErrorData, ser_rpc_response_error_data, de_rpc_response_error_data);
258
259#[serde_as]
260#[derive(Serialize, Deserialize)]
261pub enum AsRpcErrorImpl {
262 RpcRequestError(String),
263 RpcResponseError {
264 code: i64,
265 message: String,
266 #[serde_as(as = "Box<AsRpcResponseErrorData>")]
267 data: Box<RpcResponseErrorData>,
268 },
269 ParseError(String),
270 ForUser(String),
271}
272
273fn ser_rpc_error(error: &RpcError) -> AsRpcErrorImpl {
274 match error {
275 RpcError::RpcRequestError(error) => AsRpcErrorImpl::RpcRequestError(error.clone()),
276 RpcError::RpcResponseError {
277 code,
278 message,
279 data,
280 } => AsRpcErrorImpl::RpcResponseError {
281 code: *code,
282 message: message.clone(),
283 data: Box::new(clone_rpc_response_error(data)),
284 },
285 RpcError::ParseError(error) => AsRpcErrorImpl::ParseError(error.clone()),
286 RpcError::ForUser(error) => AsRpcErrorImpl::ForUser(error.clone()),
287 }
288}
289
290fn de_rpc_error(error: AsRpcErrorImpl) -> Result<RpcError, Infallible> {
291 Ok(match error {
292 AsRpcErrorImpl::RpcRequestError(error) => RpcError::RpcRequestError(error),
293 AsRpcErrorImpl::RpcResponseError {
294 code,
295 message,
296 data,
297 } => RpcError::RpcResponseError {
298 code,
299 message,
300 data: *data,
301 },
302 AsRpcErrorImpl::ParseError(error) => RpcError::ParseError(error),
303 AsRpcErrorImpl::ForUser(error) => RpcError::ForUser(error),
304 })
305}
306
307serde_conv!(pub AsRpcEeror, RpcError, ser_rpc_error, de_rpc_error);
308
309#[serde_as]
310#[derive(Serialize, Deserialize)]
311pub enum AsClientErrorKindImpl {
312 Io(#[serde_as(as = "AsIoError")] io::Error),
313 Middleware(#[serde_as(as = "AsAnyhow")] anyhow::Error),
314 RpcError(#[serde_as(as = "Box<AsRpcEeror>")] Box<RpcError>),
315 SigningError(#[serde_as(as = "AsSignerError")] SignerError),
316 TransactionError(TransactionError),
317 Custom(String),
318}
319
320#[derive(Serialize, Deserialize)]
321pub enum AsErrorKindImpl {
322 NotFound,
323 PermissionDenied,
324 ConnectionRefused,
325 ConnectionReset,
326 HostUnreachable,
327 NetworkUnreachable,
328 ConnectionAborted,
329 NotConnected,
330 AddrInUse,
331 AddrNotAvailable,
332 NetworkDown,
333 BrokenPipe,
334 AlreadyExists,
335 WouldBlock,
336 NotADirectory,
337 IsADirectory,
338 DirectoryNotEmpty,
339 ReadOnlyFilesystem,
340 StaleNetworkFileHandle,
341 InvalidInput,
342 InvalidData,
343 TimedOut,
344 WriteZero,
345 StorageFull,
346 NotSeekable,
347 QuotaExceeded,
348 FileTooLarge,
349 ResourceBusy,
350 ExecutableFileBusy,
351 Deadlock,
352 CrossesDevices,
353 TooManyLinks,
354 InvalidFilename,
355 ArgumentListTooLong,
356 Interrupted,
357 Unsupported,
358 UnexpectedEof,
359 OutOfMemory,
360 Other,
361}
362
363fn ser_error_kind(kind: &io::ErrorKind) -> AsErrorKindImpl {
364 match kind {
365 io::ErrorKind::NotFound => AsErrorKindImpl::NotFound,
366 io::ErrorKind::PermissionDenied => AsErrorKindImpl::PermissionDenied,
367 io::ErrorKind::ConnectionRefused => AsErrorKindImpl::ConnectionRefused,
368 io::ErrorKind::ConnectionReset => AsErrorKindImpl::ConnectionReset,
369 io::ErrorKind::HostUnreachable => AsErrorKindImpl::HostUnreachable,
370 io::ErrorKind::NetworkUnreachable => AsErrorKindImpl::NetworkUnreachable,
371 io::ErrorKind::ConnectionAborted => AsErrorKindImpl::ConnectionAborted,
372 io::ErrorKind::NotConnected => AsErrorKindImpl::NotConnected,
373 io::ErrorKind::AddrInUse => AsErrorKindImpl::AddrInUse,
374 io::ErrorKind::AddrNotAvailable => AsErrorKindImpl::AddrNotAvailable,
375 io::ErrorKind::NetworkDown => AsErrorKindImpl::NetworkDown,
376 io::ErrorKind::BrokenPipe => AsErrorKindImpl::BrokenPipe,
377 io::ErrorKind::AlreadyExists => AsErrorKindImpl::AlreadyExists,
378 io::ErrorKind::WouldBlock => AsErrorKindImpl::WouldBlock,
379 io::ErrorKind::NotADirectory => AsErrorKindImpl::NotADirectory,
380 io::ErrorKind::IsADirectory => AsErrorKindImpl::IsADirectory,
381 io::ErrorKind::DirectoryNotEmpty => AsErrorKindImpl::DirectoryNotEmpty,
382 io::ErrorKind::ReadOnlyFilesystem => AsErrorKindImpl::ReadOnlyFilesystem,
383 io::ErrorKind::StaleNetworkFileHandle => AsErrorKindImpl::StaleNetworkFileHandle,
384 io::ErrorKind::InvalidInput => AsErrorKindImpl::InvalidInput,
385 io::ErrorKind::InvalidData => AsErrorKindImpl::InvalidData,
386 io::ErrorKind::TimedOut => AsErrorKindImpl::TimedOut,
387 io::ErrorKind::WriteZero => AsErrorKindImpl::WriteZero,
388 io::ErrorKind::StorageFull => AsErrorKindImpl::StorageFull,
389 io::ErrorKind::NotSeekable => AsErrorKindImpl::NotSeekable,
390 io::ErrorKind::QuotaExceeded => AsErrorKindImpl::QuotaExceeded,
391 io::ErrorKind::FileTooLarge => AsErrorKindImpl::FileTooLarge,
392 io::ErrorKind::ResourceBusy => AsErrorKindImpl::ResourceBusy,
393 io::ErrorKind::ExecutableFileBusy => AsErrorKindImpl::ExecutableFileBusy,
394 io::ErrorKind::Deadlock => AsErrorKindImpl::Deadlock,
395 io::ErrorKind::CrossesDevices => AsErrorKindImpl::CrossesDevices,
396 io::ErrorKind::TooManyLinks => AsErrorKindImpl::TooManyLinks,
397 io::ErrorKind::InvalidFilename => AsErrorKindImpl::InvalidFilename,
398 io::ErrorKind::ArgumentListTooLong => AsErrorKindImpl::ArgumentListTooLong,
399 io::ErrorKind::Interrupted => AsErrorKindImpl::Interrupted,
400 io::ErrorKind::Unsupported => AsErrorKindImpl::Unsupported,
401 io::ErrorKind::UnexpectedEof => AsErrorKindImpl::UnexpectedEof,
402 io::ErrorKind::OutOfMemory => AsErrorKindImpl::OutOfMemory,
403 io::ErrorKind::Other => AsErrorKindImpl::Other,
404 _ => AsErrorKindImpl::Other,
405 }
406}
407
408fn de_error_kind(kind: AsErrorKindImpl) -> Result<io::ErrorKind, Infallible> {
409 Ok(match kind {
410 AsErrorKindImpl::NotFound => io::ErrorKind::NotFound,
411 AsErrorKindImpl::PermissionDenied => io::ErrorKind::PermissionDenied,
412 AsErrorKindImpl::ConnectionRefused => io::ErrorKind::ConnectionRefused,
413 AsErrorKindImpl::ConnectionReset => io::ErrorKind::ConnectionReset,
414 AsErrorKindImpl::HostUnreachable => io::ErrorKind::HostUnreachable,
415 AsErrorKindImpl::NetworkUnreachable => io::ErrorKind::NetworkUnreachable,
416 AsErrorKindImpl::ConnectionAborted => io::ErrorKind::ConnectionAborted,
417 AsErrorKindImpl::NotConnected => io::ErrorKind::NotConnected,
418 AsErrorKindImpl::AddrInUse => io::ErrorKind::AddrInUse,
419 AsErrorKindImpl::AddrNotAvailable => io::ErrorKind::AddrNotAvailable,
420 AsErrorKindImpl::NetworkDown => io::ErrorKind::NetworkDown,
421 AsErrorKindImpl::BrokenPipe => io::ErrorKind::BrokenPipe,
422 AsErrorKindImpl::AlreadyExists => io::ErrorKind::AlreadyExists,
423 AsErrorKindImpl::WouldBlock => io::ErrorKind::WouldBlock,
424 AsErrorKindImpl::NotADirectory => io::ErrorKind::NotADirectory,
425 AsErrorKindImpl::IsADirectory => io::ErrorKind::IsADirectory,
426 AsErrorKindImpl::DirectoryNotEmpty => io::ErrorKind::DirectoryNotEmpty,
427 AsErrorKindImpl::ReadOnlyFilesystem => io::ErrorKind::ReadOnlyFilesystem,
428 AsErrorKindImpl::StaleNetworkFileHandle => io::ErrorKind::StaleNetworkFileHandle,
429 AsErrorKindImpl::InvalidInput => io::ErrorKind::InvalidInput,
430 AsErrorKindImpl::InvalidData => io::ErrorKind::InvalidData,
431 AsErrorKindImpl::TimedOut => io::ErrorKind::TimedOut,
432 AsErrorKindImpl::WriteZero => io::ErrorKind::WriteZero,
433 AsErrorKindImpl::StorageFull => io::ErrorKind::StorageFull,
434 AsErrorKindImpl::NotSeekable => io::ErrorKind::NotSeekable,
435 AsErrorKindImpl::QuotaExceeded => io::ErrorKind::QuotaExceeded,
436 AsErrorKindImpl::FileTooLarge => io::ErrorKind::FileTooLarge,
437 AsErrorKindImpl::ResourceBusy => io::ErrorKind::ResourceBusy,
438 AsErrorKindImpl::ExecutableFileBusy => io::ErrorKind::ExecutableFileBusy,
439 AsErrorKindImpl::Deadlock => io::ErrorKind::Deadlock,
440 AsErrorKindImpl::CrossesDevices => io::ErrorKind::CrossesDevices,
441 AsErrorKindImpl::TooManyLinks => io::ErrorKind::TooManyLinks,
442 AsErrorKindImpl::InvalidFilename => io::ErrorKind::InvalidFilename,
443 AsErrorKindImpl::ArgumentListTooLong => io::ErrorKind::ArgumentListTooLong,
444 AsErrorKindImpl::Interrupted => io::ErrorKind::Interrupted,
445 AsErrorKindImpl::Unsupported => io::ErrorKind::Unsupported,
446 AsErrorKindImpl::UnexpectedEof => io::ErrorKind::UnexpectedEof,
447 AsErrorKindImpl::OutOfMemory => io::ErrorKind::OutOfMemory,
448 AsErrorKindImpl::Other => io::ErrorKind::Other,
449 })
450}
451
452serde_conv!(pub AsErrorKind, io::ErrorKind, ser_error_kind, de_error_kind);
453
454#[serde_as]
455#[derive(Serialize, Deserialize)]
456pub struct AsIoErrorImpl {
457 #[serde_as(as = "AsErrorKind")]
458 pub kind: io::ErrorKind,
459 pub msg: String,
460}
461
462fn ser_io_error(error: &io::Error) -> AsIoErrorImpl {
463 AsIoErrorImpl {
464 kind: error.kind(),
465 msg: error.to_string(),
466 }
467}
468
469fn de_io_error(error: AsIoErrorImpl) -> Result<io::Error, Infallible> {
470 Ok(io::Error::new(error.kind, error.msg))
471}
472
473serde_conv!(pub AsIoError, io::Error, ser_io_error, de_io_error);
474
475serde_conv!(
476 pub AsAnyhow,
477 anyhow::Error,
478 |error: &anyhow::Error| error.to_string(),
479 |error: String| Ok::<_, Infallible>(anyhow::Error::msg(error))
480);
481
482#[derive(Serialize, Deserialize)]
483pub enum AsPresignerErrorImpl {
484 VerificationFailure,
485}
486
487fn ser_presigner_error(error: &PresignerError) -> AsPresignerErrorImpl {
488 match error {
489 PresignerError::VerificationFailure => AsPresignerErrorImpl::VerificationFailure,
490 }
491}
492
493fn de_presigner_error(error: AsPresignerErrorImpl) -> Result<PresignerError, Infallible> {
494 Ok(match error {
495 AsPresignerErrorImpl::VerificationFailure => PresignerError::VerificationFailure,
496 })
497}
498
499serde_conv!(
500 AsPresignerError,
501 PresignerError,
502 ser_presigner_error,
503 de_presigner_error
504);
505
506#[serde_as]
507#[derive(Serialize, Deserialize)]
508pub enum AsSignerErrorImpl {
509 KeypairPubkeyMismatch,
510 NotEnoughSigners,
511 TransactionError(TransactionError),
512 Custom(String),
513 PresignerError(#[serde_as(as = "AsPresignerError")] PresignerError),
514 Connection(String),
515 InvalidInput(String),
516 NoDeviceFound,
517 Protocol(String),
518 UserCancel(String),
519 TooManySigners,
520}
521
522fn ser_signer_error(error: &SignerError) -> AsSignerErrorImpl {
523 match clone_signer_error(error) {
524 SignerError::KeypairPubkeyMismatch => AsSignerErrorImpl::KeypairPubkeyMismatch,
525 SignerError::NotEnoughSigners => AsSignerErrorImpl::NotEnoughSigners,
526 SignerError::TransactionError(transaction_error) => {
527 AsSignerErrorImpl::TransactionError(transaction_error)
528 }
529 SignerError::Custom(error) => AsSignerErrorImpl::Custom(error),
530 SignerError::PresignerError(presigner_error) => {
531 AsSignerErrorImpl::PresignerError(presigner_error)
532 }
533 SignerError::Connection(error) => AsSignerErrorImpl::Connection(error),
534 SignerError::InvalidInput(error) => AsSignerErrorImpl::InvalidInput(error),
535 SignerError::NoDeviceFound => AsSignerErrorImpl::NoDeviceFound,
536 SignerError::Protocol(error) => AsSignerErrorImpl::Protocol(error),
537 SignerError::UserCancel(error) => AsSignerErrorImpl::UserCancel(error),
538 SignerError::TooManySigners => AsSignerErrorImpl::TooManySigners,
539 }
540}
541
542fn de_signer_error(error: AsSignerErrorImpl) -> Result<SignerError, Infallible> {
543 Ok(match error {
544 AsSignerErrorImpl::KeypairPubkeyMismatch => SignerError::KeypairPubkeyMismatch,
545 AsSignerErrorImpl::NotEnoughSigners => SignerError::NotEnoughSigners,
546 AsSignerErrorImpl::TransactionError(transaction_error) => {
547 SignerError::TransactionError(transaction_error)
548 }
549 AsSignerErrorImpl::Custom(error) => SignerError::Custom(error),
550 AsSignerErrorImpl::PresignerError(presigner_error) => {
551 SignerError::PresignerError(presigner_error)
552 }
553 AsSignerErrorImpl::Connection(error) => SignerError::Connection(error),
554 AsSignerErrorImpl::InvalidInput(error) => SignerError::InvalidInput(error),
555 AsSignerErrorImpl::NoDeviceFound => SignerError::NoDeviceFound,
556 AsSignerErrorImpl::Protocol(error) => SignerError::Protocol(error),
557 AsSignerErrorImpl::UserCancel(error) => SignerError::UserCancel(error),
558 AsSignerErrorImpl::TooManySigners => SignerError::TooManySigners,
559 })
560}
561
562serde_conv!(
563 pub AsSignerError,
564 SignerError,
565 ser_signer_error,
566 de_signer_error
567);
568
569fn clone_rpc_response_error(data: &RpcResponseErrorData) -> RpcResponseErrorData {
570 match data {
571 RpcResponseErrorData::Empty => RpcResponseErrorData::Empty,
572 RpcResponseErrorData::SendTransactionPreflightFailure(result) => {
573 RpcResponseErrorData::SendTransactionPreflightFailure(result.clone())
574 }
575 RpcResponseErrorData::NodeUnhealthy { num_slots_behind } => {
576 RpcResponseErrorData::NodeUnhealthy {
577 num_slots_behind: *num_slots_behind,
578 }
579 }
580 }
581}
582
583fn clone_rpc_error(error: &RpcError) -> RpcError {
584 match error {
585 RpcError::RpcRequestError(error) => RpcError::RpcRequestError(error.clone()),
586 RpcError::RpcResponseError {
587 code,
588 message,
589 data,
590 } => RpcError::RpcResponseError {
591 code: *code,
592 message: message.clone(),
593 data: clone_rpc_response_error(data),
594 },
595 RpcError::ParseError(error) => RpcError::ParseError(error.clone()),
596 RpcError::ForUser(error) => RpcError::ForUser(error.clone()),
597 }
598}
599
600fn clone_presigner_error(error: &PresignerError) -> PresignerError {
601 match error {
602 PresignerError::VerificationFailure => PresignerError::VerificationFailure,
603 }
604}
605
606fn clone_signer_error(error: &SignerError) -> SignerError {
607 match error {
608 SignerError::KeypairPubkeyMismatch => SignerError::KeypairPubkeyMismatch,
609 SignerError::NotEnoughSigners => SignerError::NotEnoughSigners,
610 SignerError::TransactionError(error) => SignerError::TransactionError(error.clone()),
611 SignerError::Custom(error) => SignerError::Custom(error.clone()),
612 SignerError::PresignerError(error) => {
613 SignerError::PresignerError(clone_presigner_error(error))
614 }
615 SignerError::Connection(error) => SignerError::Connection(error.clone()),
616 SignerError::InvalidInput(error) => SignerError::InvalidInput(error.clone()),
617 SignerError::NoDeviceFound => SignerError::NoDeviceFound,
618 SignerError::Protocol(error) => SignerError::Protocol(error.clone()),
619 SignerError::UserCancel(error) => SignerError::UserCancel(error.clone()),
620 SignerError::TooManySigners => SignerError::TooManySigners,
621 }
622}
623
624fn ser_kind(kind: &ClientErrorKind) -> AsClientErrorKindImpl {
625 match kind {
626 ClientErrorKind::Io(error) => {
627 AsClientErrorKindImpl::Io(io::Error::new(error.kind(), error.to_string()))
628 }
629 ClientErrorKind::Reqwest(error) => AsClientErrorKindImpl::Custom(error.to_string()),
630 ClientErrorKind::Middleware(error) => {
631 AsClientErrorKindImpl::Middleware(anyhow!(format!("{:#}", error)))
632 }
633 ClientErrorKind::RpcError(error) => {
634 AsClientErrorKindImpl::RpcError(Box::new(clone_rpc_error(error)))
635 }
636 ClientErrorKind::SerdeJson(error) => AsClientErrorKindImpl::Custom(error.to_string()),
637 ClientErrorKind::SigningError(error) => {
638 AsClientErrorKindImpl::SigningError(clone_signer_error(error))
639 }
640 ClientErrorKind::TransactionError(error) => {
641 AsClientErrorKindImpl::TransactionError(error.clone())
642 }
643 ClientErrorKind::Custom(error) => AsClientErrorKindImpl::Custom(error.clone()),
644 }
645}
646
647fn de_kind(kind: AsClientErrorKindImpl) -> Result<ClientErrorKind, Infallible> {
648 Ok(match kind {
649 AsClientErrorKindImpl::Io(error) => ClientErrorKind::Io(error),
650 AsClientErrorKindImpl::Middleware(error) => ClientErrorKind::Middleware(error),
651 AsClientErrorKindImpl::RpcError(rpc_error) => ClientErrorKind::RpcError(*rpc_error),
652 AsClientErrorKindImpl::SigningError(signer_error) => {
653 ClientErrorKind::SigningError(signer_error)
654 }
655 AsClientErrorKindImpl::TransactionError(transaction_error) => {
656 ClientErrorKind::TransactionError(transaction_error)
657 }
658 AsClientErrorKindImpl::Custom(error) => ClientErrorKind::Custom(error),
659 })
660}
661
662serde_conv!(pub AsClientErrorKind, ClientErrorKind, ser_kind, de_kind);
663
664#[serde_as]
665#[derive(Serialize, Deserialize)]
666pub struct AsClientErrorImpl {
667 #[serde_as(as = "Option<AsRpcRequest>")]
668 pub request: Option<RpcRequest>,
669 #[serde_as(as = "Box<AsClientErrorKind>")]
670 pub kind: Box<ClientErrorKind>,
671}
672
673fn clone_client_error_kind(kind: &ClientErrorKind) -> Box<ClientErrorKind> {
674 Box::new(de_kind(ser_kind(kind)).unwrap())
675}
676
677fn ser_client_error(error: &ClientError) -> AsClientErrorImpl {
678 AsClientErrorImpl {
679 request: error.request,
680 kind: clone_client_error_kind(&error.kind),
681 }
682}
683
684fn de_client_error(error: AsClientErrorImpl) -> Result<ClientError, Infallible> {
685 Ok(ClientError {
686 request: error.request,
687 kind: error.kind,
688 })
689}
690
691serde_conv!(
692 pub AsClientError,
693 ClientError,
694 ser_client_error,
695 de_client_error
696);
697
698#[derive(Serialize, Deserialize)]
699pub enum AsCompileErrorImpl {
700 AccountIndexOverflow,
701 AddressTableLookupIndexOverflow,
702 UnknownInstructionKey(Pubkey),
703}
704
705fn ser_CompileError(error: &CompileError) -> AsCompileErrorImpl {
706 match error {
707 CompileError::AccountIndexOverflow => AsCompileErrorImpl::AccountIndexOverflow,
708 CompileError::AddressTableLookupIndexOverflow => {
709 AsCompileErrorImpl::AddressTableLookupIndexOverflow
710 }
711 CompileError::UnknownInstructionKey(pubkey) => {
712 AsCompileErrorImpl::UnknownInstructionKey(*pubkey)
713 }
714 }
715}
716
717fn de_CompileError(error: AsCompileErrorImpl) -> Result<CompileError, Infallible> {
718 Ok(match error {
719 AsCompileErrorImpl::AccountIndexOverflow => CompileError::AccountIndexOverflow,
720 AsCompileErrorImpl::AddressTableLookupIndexOverflow => {
721 CompileError::AddressTableLookupIndexOverflow
722 }
723 AsCompileErrorImpl::UnknownInstructionKey(pubkey) => {
724 CompileError::UnknownInstructionKey(pubkey)
725 }
726 })
727}
728
729serde_conv!(pub AsCompileError, CompileError, ser_CompileError, de_CompileError);
730
731#[derive(Serialize, Deserialize)]
732pub enum AsSanitizeErrorImpl {
733 IndexOutOfBounds,
734 ValueOutOfBounds,
735 InvalidValue,
736}
737
738fn ser_SanitizeError(error: &SanitizeError) -> AsSanitizeErrorImpl {
739 match error {
740 SanitizeError::IndexOutOfBounds => AsSanitizeErrorImpl::IndexOutOfBounds,
741 SanitizeError::ValueOutOfBounds => AsSanitizeErrorImpl::ValueOutOfBounds,
742 SanitizeError::InvalidValue => AsSanitizeErrorImpl::InvalidValue,
743 }
744}
745
746fn de_SanitizeError(error: AsSanitizeErrorImpl) -> Result<SanitizeError, Infallible> {
747 Ok(match error {
748 AsSanitizeErrorImpl::IndexOutOfBounds => SanitizeError::IndexOutOfBounds,
749 AsSanitizeErrorImpl::ValueOutOfBounds => SanitizeError::ValueOutOfBounds,
750 AsSanitizeErrorImpl::InvalidValue => SanitizeError::InvalidValue,
751 })
752}
753
754serde_conv!(pub AsSanitizeError, SanitizeError, ser_SanitizeError, de_SanitizeError);
755
756#[derive(Serialize, Deserialize)]
757pub enum AsMailboxErrorImpl {
758 Closed,
759 Timeout,
760}
761
762fn ser_MailboxError(error: &MailboxError) -> AsMailboxErrorImpl {
763 match error {
764 MailboxError::Closed => AsMailboxErrorImpl::Closed,
765 MailboxError::Timeout => AsMailboxErrorImpl::Timeout,
766 }
767}
768
769fn de_MailboxError(error: AsMailboxErrorImpl) -> Result<MailboxError, Infallible> {
770 Ok(match error {
771 AsMailboxErrorImpl::Closed => MailboxError::Closed,
772 AsMailboxErrorImpl::Timeout => MailboxError::Timeout,
773 })
774}
775
776serde_conv!(pub AsMailboxError, MailboxError, ser_MailboxError, de_MailboxError);
777
778serde_conv!(pub AsCancelled, Canceled, |_| (), |_: ()| Ok::<_, Infallible>(Canceled));