1use std::{any::Any, error::Error, fmt::Display};
2
3use async_trait::async_trait;
4use serde::{de::DeserializeOwned, Deserialize, Serialize};
5use serde_with::serde_as;
6use starknet_rust_core::{
7 serde::unsigned_field_element::UfeHex,
8 types::{
9 requests::*, BlockHashAndNumber, BlockId, BroadcastedDeclareTransaction,
10 BroadcastedDeployAccountTransaction, BroadcastedInvokeTransaction, BroadcastedTransaction,
11 ConfirmedBlockId, ContractClass, ContractErrorData, ContractStorageKeys,
12 DeclareTransactionResult, DeployAccountTransactionResult, EventFilter, EventFilterWithPage,
13 EventsPage, FeeEstimate, Felt as FeltPrimitive, FunctionCall, Hash256,
14 InvokeTransactionResult, MaybePreConfirmedBlockWithReceipts,
15 MaybePreConfirmedBlockWithTxHashes, MaybePreConfirmedBlockWithTxs,
16 MaybePreConfirmedStateUpdate, MessageFeeEstimate, MessageStatus, MsgFromL1,
17 NoTraceAvailableErrorData, ResultPageRequest, SimulatedTransaction, SimulationFlag,
18 SimulationFlagForEstimateFee, StarknetError, StorageProof, SubscriptionId, SyncStatusType,
19 Transaction, TransactionExecutionErrorData, TransactionReceiptWithBlockInfo,
20 TransactionStatus, TransactionTrace, TransactionTraceWithHash,
21 },
22};
23
24use crate::{
25 provider::ProviderImplError, Provider, ProviderError, ProviderRequestData,
26 ProviderResponseData, StreamUpdateData,
27};
28
29mod transports;
30pub use transports::{HttpTransport, HttpTransportError, JsonRpcTransport};
31#[cfg(feature = "worker")]
32pub use transports::{WorkersTransport, WorkersTransportError};
33
34#[derive(Debug, Clone)]
39pub struct JsonRpcClient<T> {
40 transport: T,
41}
42
43#[derive(Debug, Clone, Copy, Serialize, Deserialize)]
45pub enum JsonRpcMethod {
46 #[serde(rename = "starknet_specVersion")]
48 SpecVersion,
49 #[serde(rename = "starknet_getBlockWithTxHashes")]
51 GetBlockWithTxHashes,
52 #[serde(rename = "starknet_getBlockWithTxs")]
54 GetBlockWithTxs,
55 #[serde(rename = "starknet_getBlockWithReceipts")]
57 GetBlockWithReceipts,
58 #[serde(rename = "starknet_getStateUpdate")]
60 GetStateUpdate,
61 #[serde(rename = "starknet_getStorageAt")]
63 GetStorageAt,
64 #[serde(rename = "starknet_getMessagesStatus")]
66 GetMessagesStatus,
67 #[serde(rename = "starknet_getTransactionStatus")]
69 GetTransactionStatus,
70 #[serde(rename = "starknet_getTransactionByHash")]
72 GetTransactionByHash,
73 #[serde(rename = "starknet_getTransactionByBlockIdAndIndex")]
75 GetTransactionByBlockIdAndIndex,
76 #[serde(rename = "starknet_getTransactionReceipt")]
78 GetTransactionReceipt,
79 #[serde(rename = "starknet_getClass")]
81 GetClass,
82 #[serde(rename = "starknet_getClassHashAt")]
84 GetClassHashAt,
85 #[serde(rename = "starknet_getClassAt")]
87 GetClassAt,
88 #[serde(rename = "starknet_getBlockTransactionCount")]
90 GetBlockTransactionCount,
91 #[serde(rename = "starknet_call")]
93 Call,
94 #[serde(rename = "starknet_estimateFee")]
96 EstimateFee,
97 #[serde(rename = "starknet_estimateMessageFee")]
99 EstimateMessageFee,
100 #[serde(rename = "starknet_blockNumber")]
102 BlockNumber,
103 #[serde(rename = "starknet_blockHashAndNumber")]
105 BlockHashAndNumber,
106 #[serde(rename = "starknet_chainId")]
108 ChainId,
109 #[serde(rename = "starknet_syncing")]
111 Syncing,
112 #[serde(rename = "starknet_getEvents")]
114 GetEvents,
115 #[serde(rename = "starknet_getNonce")]
117 GetNonce,
118 #[serde(rename = "starknet_getStorageProof")]
120 GetStorageProof,
121 #[serde(rename = "starknet_addInvokeTransaction")]
123 AddInvokeTransaction,
124 #[serde(rename = "starknet_addDeclareTransaction")]
126 AddDeclareTransaction,
127 #[serde(rename = "starknet_addDeployAccountTransaction")]
129 AddDeployAccountTransaction,
130 #[serde(rename = "starknet_traceTransaction")]
132 TraceTransaction,
133 #[serde(rename = "starknet_simulateTransactions")]
135 SimulateTransactions,
136 #[serde(rename = "starknet_traceBlockTransactions")]
138 TraceBlockTransactions,
139 #[serde(rename = "starknet_subscribeNewHeads")]
141 SubscribeNewHeads,
142 #[serde(rename = "starknet_subscriptionNewHeads")]
144 SubscriptionNewHeads,
145 #[serde(rename = "starknet_subscribeEvents")]
147 SubscribeEvents,
148 #[serde(rename = "starknet_subscriptionEvents")]
150 SubscriptionEvents,
151 #[serde(rename = "starknet_subscribeTransactionStatus")]
153 SubscribeTransactionStatus,
154 #[serde(rename = "starknet_subscriptionTransactionStatus")]
156 SubscriptionTransactionStatus,
157 #[serde(rename = "starknet_subscribeNewTransactionReceipts")]
159 SubscribeNewTransactionReceipts,
160 #[serde(rename = "starknet_subscriptionNewTransactionReceipts")]
162 SubscriptionNewTransactionReceipts,
163 #[serde(rename = "starknet_subscribeNewTransactions")]
165 SubscribeNewTransactions,
166 #[serde(rename = "starknet_subscriptionNewTransaction")]
168 SubscriptionNewTransaction,
169 #[serde(rename = "starknet_subscriptionReorg")]
171 SubscriptionReorg,
172 #[serde(rename = "starknet_unsubscribe")]
174 Unsubscribe,
175}
176
177#[derive(Debug, Clone)]
179pub struct JsonRpcRequest {
180 pub id: u64,
182 pub data: ProviderRequestData,
184}
185
186#[derive(Debug, Clone)]
188pub struct JsonRpcStreamUpdate {
189 pub data: StreamUpdateData,
191}
192
193#[derive(Debug, thiserror::Error)]
195pub enum JsonRpcClientError<T> {
196 #[error(transparent)]
198 JsonError(serde_json::Error),
199 #[error(transparent)]
201 TransportError(T),
202 #[error(transparent)]
204 JsonRpcError(JsonRpcError),
205}
206
207#[derive(Debug, Clone, Deserialize)]
209pub struct JsonRpcError {
210 pub code: i64,
212 pub message: String,
214 #[serde(skip_serializing_if = "Option::is_none")]
216 pub data: Option<serde_json::Value>,
217}
218
219#[derive(Debug, Clone, Deserialize)]
221#[serde(untagged)]
222pub enum JsonRpcResponse<T> {
223 Success {
225 id: u64,
227 result: T,
229 },
230 Error {
232 id: u64,
234 error: JsonRpcError,
236 },
237}
238
239#[derive(Debug, thiserror::Error)]
248pub enum JsonRpcErrorConversionError {
249 #[error("unknown error code")]
251 UnknownCode,
252 #[error("missing data field")]
254 MissingData,
255 #[error("unable to parse the data field")]
257 DataParsingFailure,
258}
259
260#[serde_as]
261#[derive(Serialize, Deserialize)]
262struct Felt(#[serde_as(as = "UfeHex")] pub FeltPrimitive);
263
264#[serde_as]
265#[derive(Serialize, Deserialize)]
266struct FeltArray(#[serde_as(as = "Vec<UfeHex>")] pub Vec<FeltPrimitive>);
267
268impl<T> JsonRpcClient<T> {
269 pub const fn new(transport: T) -> Self {
271 Self { transport }
272 }
273}
274
275impl<T> JsonRpcClient<T>
276where
277 T: 'static + JsonRpcTransport + Send + Sync,
278{
279 async fn send_request<P, R>(&self, method: JsonRpcMethod, params: P) -> Result<R, ProviderError>
280 where
281 P: Serialize + Send + Sync,
282 R: DeserializeOwned + Send,
283 {
284 match self
285 .transport
286 .send_request(method, params)
287 .await
288 .map_err(JsonRpcClientError::TransportError)?
289 {
290 JsonRpcResponse::Success { result, .. } => Ok(result),
291 JsonRpcResponse::Error { error, .. } => {
292 Err(match TryInto::<StarknetError>::try_into(&error) {
293 Ok(error) => ProviderError::StarknetError(error),
294 Err(_) => JsonRpcClientError::<T::Error>::JsonRpcError(error).into(),
295 })
296 }
297 }
298 }
299
300 async fn send_requests<R>(
301 &self,
302 requests: R,
303 ) -> Result<Vec<ProviderResponseData>, ProviderError>
304 where
305 R: AsRef<[ProviderRequestData]> + Send + Sync,
306 {
307 let mut results = vec![];
308
309 let responses = self
310 .transport
311 .send_requests(requests.as_ref().to_vec())
312 .await
313 .map_err(JsonRpcClientError::TransportError)?;
314
315 for (request, response) in requests.as_ref().iter().zip(responses.into_iter()) {
316 match response {
317 JsonRpcResponse::Success { result, .. } => {
318 let result = match request {
319 ProviderRequestData::SpecVersion(_) => ProviderResponseData::SpecVersion(
320 String::deserialize(result)
321 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
322 ),
323 ProviderRequestData::GetBlockWithTxHashes(_) => {
324 ProviderResponseData::GetBlockWithTxHashes(
325 MaybePreConfirmedBlockWithTxHashes::deserialize(result)
326 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
327 )
328 }
329 ProviderRequestData::GetBlockWithTxs(_) => {
330 ProviderResponseData::GetBlockWithTxs(
331 MaybePreConfirmedBlockWithTxs::deserialize(result)
332 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
333 )
334 }
335 ProviderRequestData::GetBlockWithReceipts(_) => {
336 ProviderResponseData::GetBlockWithReceipts(
337 MaybePreConfirmedBlockWithReceipts::deserialize(result)
338 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
339 )
340 }
341 ProviderRequestData::GetStateUpdate(_) => {
342 ProviderResponseData::GetStateUpdate(
343 MaybePreConfirmedStateUpdate::deserialize(result)
344 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
345 )
346 }
347 ProviderRequestData::GetStorageAt(_) => ProviderResponseData::GetStorageAt(
348 Felt::deserialize(result)
349 .map_err(JsonRpcClientError::<T::Error>::JsonError)?
350 .0,
351 ),
352 ProviderRequestData::GetMessagesStatus(_) => {
353 ProviderResponseData::GetMessagesStatus(
354 Vec::<MessageStatus>::deserialize(result)
355 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
356 )
357 }
358 ProviderRequestData::GetTransactionStatus(_) => {
359 ProviderResponseData::GetTransactionStatus(
360 TransactionStatus::deserialize(result)
361 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
362 )
363 }
364 ProviderRequestData::GetTransactionByHash(_) => {
365 ProviderResponseData::GetTransactionByHash(
366 Transaction::deserialize(result)
367 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
368 )
369 }
370 ProviderRequestData::GetTransactionByBlockIdAndIndex(_) => {
371 ProviderResponseData::GetTransactionByBlockIdAndIndex(
372 Transaction::deserialize(result)
373 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
374 )
375 }
376 ProviderRequestData::GetTransactionReceipt(_) => {
377 ProviderResponseData::GetTransactionReceipt(
378 TransactionReceiptWithBlockInfo::deserialize(result)
379 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
380 )
381 }
382 ProviderRequestData::GetClass(_) => ProviderResponseData::GetClass(
383 ContractClass::deserialize(result)
384 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
385 ),
386 ProviderRequestData::GetClassHashAt(_) => {
387 ProviderResponseData::GetClassHashAt(
388 Felt::deserialize(result)
389 .map_err(JsonRpcClientError::<T::Error>::JsonError)?
390 .0,
391 )
392 }
393 ProviderRequestData::GetClassAt(_) => ProviderResponseData::GetClassAt(
394 ContractClass::deserialize(result)
395 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
396 ),
397 ProviderRequestData::GetBlockTransactionCount(_) => {
398 ProviderResponseData::GetBlockTransactionCount(
399 u64::deserialize(result)
400 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
401 )
402 }
403 ProviderRequestData::Call(_) => ProviderResponseData::Call(
404 FeltArray::deserialize(result)
405 .map_err(JsonRpcClientError::<T::Error>::JsonError)?
406 .0,
407 ),
408 ProviderRequestData::EstimateFee(_) => ProviderResponseData::EstimateFee(
409 Vec::<FeeEstimate>::deserialize(result)
410 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
411 ),
412 ProviderRequestData::EstimateMessageFee(_) => {
413 ProviderResponseData::EstimateMessageFee(
414 FeeEstimate::deserialize(result)
415 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
416 )
417 }
418 ProviderRequestData::BlockNumber(_) => ProviderResponseData::BlockNumber(
419 u64::deserialize(result)
420 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
421 ),
422 ProviderRequestData::BlockHashAndNumber(_) => {
423 ProviderResponseData::BlockHashAndNumber(
424 BlockHashAndNumber::deserialize(result)
425 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
426 )
427 }
428 ProviderRequestData::ChainId(_) => ProviderResponseData::ChainId(
429 Felt::deserialize(result)
430 .map_err(JsonRpcClientError::<T::Error>::JsonError)?
431 .0,
432 ),
433 ProviderRequestData::Syncing(_) => ProviderResponseData::Syncing(
434 SyncStatusType::deserialize(result)
435 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
436 ),
437 ProviderRequestData::GetEvents(_) => ProviderResponseData::GetEvents(
438 EventsPage::deserialize(result)
439 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
440 ),
441 ProviderRequestData::GetNonce(_) => ProviderResponseData::GetNonce(
442 Felt::deserialize(result)
443 .map_err(JsonRpcClientError::<T::Error>::JsonError)?
444 .0,
445 ),
446 ProviderRequestData::GetStorageProof(_) => {
447 ProviderResponseData::GetStorageProof(
448 StorageProof::deserialize(result)
449 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
450 )
451 }
452 ProviderRequestData::AddInvokeTransaction(_) => {
453 ProviderResponseData::AddInvokeTransaction(
454 InvokeTransactionResult::deserialize(result)
455 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
456 )
457 }
458 ProviderRequestData::AddDeclareTransaction(_) => {
459 ProviderResponseData::AddDeclareTransaction(
460 DeclareTransactionResult::deserialize(result)
461 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
462 )
463 }
464 ProviderRequestData::AddDeployAccountTransaction(_) => {
465 ProviderResponseData::AddDeployAccountTransaction(
466 DeployAccountTransactionResult::deserialize(result)
467 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
468 )
469 }
470 ProviderRequestData::TraceTransaction(_) => {
471 ProviderResponseData::TraceTransaction(
472 TransactionTrace::deserialize(result)
473 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
474 )
475 }
476 ProviderRequestData::SimulateTransactions(_) => {
477 ProviderResponseData::SimulateTransactions(
478 Vec::<SimulatedTransaction>::deserialize(result)
479 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
480 )
481 }
482 ProviderRequestData::TraceBlockTransactions(_) => {
483 ProviderResponseData::TraceBlockTransactions(
484 Vec::<TransactionTraceWithHash>::deserialize(result)
485 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
486 )
487 }
488 ProviderRequestData::SubscribeNewHeads(_) => {
489 ProviderResponseData::SubscribeNewHeads(
490 SubscriptionId::deserialize(result)
491 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
492 )
493 }
494 ProviderRequestData::SubscribeEvents(_) => {
495 ProviderResponseData::SubscribeEvents(
496 SubscriptionId::deserialize(result)
497 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
498 )
499 }
500 ProviderRequestData::SubscribeTransactionStatus(_) => {
501 ProviderResponseData::SubscribeTransactionStatus(
502 SubscriptionId::deserialize(result)
503 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
504 )
505 }
506 ProviderRequestData::SubscribeNewTransactionReceipts(_) => {
507 ProviderResponseData::SubscribeNewTransactionReceipts(
508 SubscriptionId::deserialize(result)
509 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
510 )
511 }
512 ProviderRequestData::SubscribeNewTransactions(_) => {
513 ProviderResponseData::SubscribeNewTransactions(
514 SubscriptionId::deserialize(result)
515 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
516 )
517 }
518 ProviderRequestData::Unsubscribe(_) => ProviderResponseData::Unsubscribe(
519 bool::deserialize(result)
520 .map_err(JsonRpcClientError::<T::Error>::JsonError)?,
521 ),
522 };
523
524 results.push(result);
525 }
526 JsonRpcResponse::Error { error, .. } => {
528 return Err(match TryInto::<StarknetError>::try_into(&error) {
529 Ok(error) => ProviderError::StarknetError(error),
530 Err(_) => JsonRpcClientError::<T::Error>::JsonRpcError(error).into(),
531 })
532 }
533 }
534 }
535
536 Ok(results)
537 }
538}
539
540#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
541#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
542impl<T> Provider for JsonRpcClient<T>
543where
544 T: 'static + JsonRpcTransport + Sync + Send,
545{
546 async fn spec_version(&self) -> Result<String, ProviderError> {
548 self.send_request(JsonRpcMethod::SpecVersion, SpecVersionRequest)
549 .await
550 }
551
552 async fn starknet_version<B>(&self, block_id: B) -> Result<String, ProviderError>
554 where
555 B: AsRef<BlockId> + Send + Sync,
556 {
557 Ok(match self.get_block_with_tx_hashes(block_id).await? {
558 MaybePreConfirmedBlockWithTxHashes::Block(block) => block.starknet_version,
559 MaybePreConfirmedBlockWithTxHashes::PreConfirmedBlock(block) => block.starknet_version,
560 })
561 }
562
563 async fn get_block_with_tx_hashes<B>(
565 &self,
566 block_id: B,
567 ) -> Result<MaybePreConfirmedBlockWithTxHashes, ProviderError>
568 where
569 B: AsRef<BlockId> + Send + Sync,
570 {
571 self.send_request(
572 JsonRpcMethod::GetBlockWithTxHashes,
573 GetBlockWithTxHashesRequestRef {
574 block_id: block_id.as_ref(),
575 },
576 )
577 .await
578 }
579
580 async fn get_block_with_txs<B>(
582 &self,
583 block_id: B,
584 ) -> Result<MaybePreConfirmedBlockWithTxs, ProviderError>
585 where
586 B: AsRef<BlockId> + Send + Sync,
587 {
588 self.send_request(
589 JsonRpcMethod::GetBlockWithTxs,
590 GetBlockWithTxsRequestRef {
591 block_id: block_id.as_ref(),
592 },
593 )
594 .await
595 }
596
597 async fn get_block_with_receipts<B>(
599 &self,
600 block_id: B,
601 ) -> Result<MaybePreConfirmedBlockWithReceipts, ProviderError>
602 where
603 B: AsRef<BlockId> + Send + Sync,
604 {
605 self.send_request(
606 JsonRpcMethod::GetBlockWithReceipts,
607 GetBlockWithReceiptsRequestRef {
608 block_id: block_id.as_ref(),
609 },
610 )
611 .await
612 }
613
614 async fn get_state_update<B>(
616 &self,
617 block_id: B,
618 ) -> Result<MaybePreConfirmedStateUpdate, ProviderError>
619 where
620 B: AsRef<BlockId> + Send + Sync,
621 {
622 self.send_request(
623 JsonRpcMethod::GetStateUpdate,
624 GetStateUpdateRequestRef {
625 block_id: block_id.as_ref(),
626 },
627 )
628 .await
629 }
630
631 async fn get_storage_at<A, K, B>(
633 &self,
634 contract_address: A,
635 key: K,
636 block_id: B,
637 ) -> Result<FeltPrimitive, ProviderError>
638 where
639 A: AsRef<FeltPrimitive> + Send + Sync,
640 K: AsRef<FeltPrimitive> + Send + Sync,
641 B: AsRef<BlockId> + Send + Sync,
642 {
643 Ok(self
644 .send_request::<_, Felt>(
645 JsonRpcMethod::GetStorageAt,
646 GetStorageAtRequestRef {
647 contract_address: contract_address.as_ref(),
648 key: key.as_ref(),
649 block_id: block_id.as_ref(),
650 },
651 )
652 .await?
653 .0)
654 }
655
656 async fn get_messages_status(
659 &self,
660 transaction_hash: Hash256,
661 ) -> Result<Vec<MessageStatus>, ProviderError> {
662 self.send_request(
663 JsonRpcMethod::GetMessagesStatus,
664 GetMessagesStatusRequestRef {
665 transaction_hash: &transaction_hash,
666 },
667 )
668 .await
669 }
670
671 async fn get_transaction_status<H>(
674 &self,
675 transaction_hash: H,
676 ) -> Result<TransactionStatus, ProviderError>
677 where
678 H: AsRef<FeltPrimitive> + Send + Sync,
679 {
680 self.send_request(
681 JsonRpcMethod::GetTransactionStatus,
682 GetTransactionStatusRequestRef {
683 transaction_hash: transaction_hash.as_ref(),
684 },
685 )
686 .await
687 }
688
689 async fn get_transaction_by_hash<H>(
691 &self,
692 transaction_hash: H,
693 ) -> Result<Transaction, ProviderError>
694 where
695 H: AsRef<FeltPrimitive> + Send + Sync,
696 {
697 self.send_request(
698 JsonRpcMethod::GetTransactionByHash,
699 GetTransactionByHashRequestRef {
700 transaction_hash: transaction_hash.as_ref(),
701 },
702 )
703 .await
704 }
705
706 async fn get_transaction_by_block_id_and_index<B>(
708 &self,
709 block_id: B,
710 index: u64,
711 ) -> Result<Transaction, ProviderError>
712 where
713 B: AsRef<BlockId> + Send + Sync,
714 {
715 self.send_request(
716 JsonRpcMethod::GetTransactionByBlockIdAndIndex,
717 GetTransactionByBlockIdAndIndexRequestRef {
718 block_id: block_id.as_ref(),
719 index: &index,
720 },
721 )
722 .await
723 }
724
725 async fn get_transaction_receipt<H>(
727 &self,
728 transaction_hash: H,
729 ) -> Result<TransactionReceiptWithBlockInfo, ProviderError>
730 where
731 H: AsRef<FeltPrimitive> + Send + Sync,
732 {
733 self.send_request(
734 JsonRpcMethod::GetTransactionReceipt,
735 GetTransactionReceiptRequestRef {
736 transaction_hash: transaction_hash.as_ref(),
737 },
738 )
739 .await
740 }
741
742 async fn get_class<B, H>(
744 &self,
745 block_id: B,
746 class_hash: H,
747 ) -> Result<ContractClass, ProviderError>
748 where
749 B: AsRef<BlockId> + Send + Sync,
750 H: AsRef<FeltPrimitive> + Send + Sync,
751 {
752 self.send_request(
753 JsonRpcMethod::GetClass,
754 GetClassRequestRef {
755 block_id: block_id.as_ref(),
756 class_hash: class_hash.as_ref(),
757 },
758 )
759 .await
760 }
761
762 async fn get_class_hash_at<B, A>(
764 &self,
765 block_id: B,
766 contract_address: A,
767 ) -> Result<FeltPrimitive, ProviderError>
768 where
769 B: AsRef<BlockId> + Send + Sync,
770 A: AsRef<FeltPrimitive> + Send + Sync,
771 {
772 Ok(self
773 .send_request::<_, Felt>(
774 JsonRpcMethod::GetClassHashAt,
775 GetClassHashAtRequestRef {
776 block_id: block_id.as_ref(),
777 contract_address: contract_address.as_ref(),
778 },
779 )
780 .await?
781 .0)
782 }
783
784 async fn get_class_at<B, A>(
786 &self,
787 block_id: B,
788 contract_address: A,
789 ) -> Result<ContractClass, ProviderError>
790 where
791 B: AsRef<BlockId> + Send + Sync,
792 A: AsRef<FeltPrimitive> + Send + Sync,
793 {
794 self.send_request(
795 JsonRpcMethod::GetClassAt,
796 GetClassAtRequestRef {
797 block_id: block_id.as_ref(),
798 contract_address: contract_address.as_ref(),
799 },
800 )
801 .await
802 }
803
804 async fn get_block_transaction_count<B>(&self, block_id: B) -> Result<u64, ProviderError>
806 where
807 B: AsRef<BlockId> + Send + Sync,
808 {
809 self.send_request(
810 JsonRpcMethod::GetBlockTransactionCount,
811 GetBlockTransactionCountRequestRef {
812 block_id: block_id.as_ref(),
813 },
814 )
815 .await
816 }
817
818 async fn call<R, B>(&self, request: R, block_id: B) -> Result<Vec<FeltPrimitive>, ProviderError>
820 where
821 R: AsRef<FunctionCall> + Send + Sync,
822 B: AsRef<BlockId> + Send + Sync,
823 {
824 Ok(self
825 .send_request::<_, FeltArray>(
826 JsonRpcMethod::Call,
827 CallRequestRef {
828 request: request.as_ref(),
829 block_id: block_id.as_ref(),
830 },
831 )
832 .await?
833 .0)
834 }
835
836 async fn estimate_fee<R, S, B>(
838 &self,
839 request: R,
840 simulation_flags: S,
841 block_id: B,
842 ) -> Result<Vec<FeeEstimate>, ProviderError>
843 where
844 R: AsRef<[BroadcastedTransaction]> + Send + Sync,
845 S: AsRef<[SimulationFlagForEstimateFee]> + Send + Sync,
846 B: AsRef<BlockId> + Send + Sync,
847 {
848 self.send_request(
849 JsonRpcMethod::EstimateFee,
850 EstimateFeeRequestRef {
851 request: request.as_ref(),
852 simulation_flags: simulation_flags.as_ref(),
853 block_id: block_id.as_ref(),
854 },
855 )
856 .await
857 }
858
859 async fn estimate_message_fee<M, B>(
861 &self,
862 message: M,
863 block_id: B,
864 ) -> Result<MessageFeeEstimate, ProviderError>
865 where
866 M: AsRef<MsgFromL1> + Send + Sync,
867 B: AsRef<BlockId> + Send + Sync,
868 {
869 self.send_request(
870 JsonRpcMethod::EstimateMessageFee,
871 EstimateMessageFeeRequestRef {
872 message: message.as_ref(),
873 block_id: block_id.as_ref(),
874 },
875 )
876 .await
877 }
878
879 async fn block_number(&self) -> Result<u64, ProviderError> {
881 self.send_request(JsonRpcMethod::BlockNumber, BlockNumberRequest)
882 .await
883 }
884
885 async fn block_hash_and_number(&self) -> Result<BlockHashAndNumber, ProviderError> {
887 self.send_request(JsonRpcMethod::BlockHashAndNumber, BlockHashAndNumberRequest)
888 .await
889 }
890
891 async fn chain_id(&self) -> Result<FeltPrimitive, ProviderError> {
893 Ok(self
894 .send_request::<_, Felt>(JsonRpcMethod::ChainId, ChainIdRequest)
895 .await?
896 .0)
897 }
898
899 async fn syncing(&self) -> Result<SyncStatusType, ProviderError> {
901 self.send_request(JsonRpcMethod::Syncing, SyncingRequest)
902 .await
903 }
904
905 async fn get_events(
907 &self,
908 filter: EventFilter,
909 continuation_token: Option<String>,
910 chunk_size: u64,
911 ) -> Result<EventsPage, ProviderError> {
912 self.send_request(
913 JsonRpcMethod::GetEvents,
914 GetEventsRequestRef {
915 filter: &EventFilterWithPage {
916 event_filter: filter,
917 result_page_request: ResultPageRequest {
918 continuation_token,
919 chunk_size,
920 },
921 },
922 },
923 )
924 .await
925 }
926
927 async fn get_nonce<B, A>(
929 &self,
930 block_id: B,
931 contract_address: A,
932 ) -> Result<FeltPrimitive, ProviderError>
933 where
934 B: AsRef<BlockId> + Send + Sync,
935 A: AsRef<FeltPrimitive> + Send + Sync,
936 {
937 Ok(self
938 .send_request::<_, Felt>(
939 JsonRpcMethod::GetNonce,
940 GetNonceRequestRef {
941 block_id: block_id.as_ref(),
942 contract_address: contract_address.as_ref(),
943 },
944 )
945 .await?
946 .0)
947 }
948
949 async fn get_storage_proof<B, H, A, K>(
953 &self,
954 block_id: B,
955 class_hashes: H,
956 contract_addresses: A,
957 contracts_storage_keys: K,
958 ) -> Result<StorageProof, ProviderError>
959 where
960 B: AsRef<ConfirmedBlockId> + Send + Sync,
961 H: AsRef<[FeltPrimitive]> + Send + Sync,
962 A: AsRef<[FeltPrimitive]> + Send + Sync,
963 K: AsRef<[ContractStorageKeys]> + Send + Sync,
964 {
965 self.send_request(
966 JsonRpcMethod::GetStorageProof,
967 GetStorageProofRequestRef {
968 block_id: block_id.as_ref(),
969 class_hashes: Some(class_hashes.as_ref()),
970 contract_addresses: Some(contract_addresses.as_ref()),
971 contracts_storage_keys: Some(contracts_storage_keys.as_ref()),
972 },
973 )
974 .await
975 }
976
977 async fn add_invoke_transaction<I>(
979 &self,
980 invoke_transaction: I,
981 ) -> Result<InvokeTransactionResult, ProviderError>
982 where
983 I: AsRef<BroadcastedInvokeTransaction> + Send + Sync,
984 {
985 self.send_request(
986 JsonRpcMethod::AddInvokeTransaction,
987 AddInvokeTransactionRequestRef {
988 invoke_transaction: invoke_transaction.as_ref(),
989 },
990 )
991 .await
992 }
993
994 async fn add_declare_transaction<D>(
996 &self,
997 declare_transaction: D,
998 ) -> Result<DeclareTransactionResult, ProviderError>
999 where
1000 D: AsRef<BroadcastedDeclareTransaction> + Send + Sync,
1001 {
1002 self.send_request(
1003 JsonRpcMethod::AddDeclareTransaction,
1004 AddDeclareTransactionRequestRef {
1005 declare_transaction: declare_transaction.as_ref(),
1006 },
1007 )
1008 .await
1009 }
1010
1011 async fn add_deploy_account_transaction<D>(
1013 &self,
1014 deploy_account_transaction: D,
1015 ) -> Result<DeployAccountTransactionResult, ProviderError>
1016 where
1017 D: AsRef<BroadcastedDeployAccountTransaction> + Send + Sync,
1018 {
1019 self.send_request(
1020 JsonRpcMethod::AddDeployAccountTransaction,
1021 AddDeployAccountTransactionRequestRef {
1022 deploy_account_transaction: deploy_account_transaction.as_ref(),
1023 },
1024 )
1025 .await
1026 }
1027
1028 async fn trace_transaction<H>(
1031 &self,
1032 transaction_hash: H,
1033 ) -> Result<TransactionTrace, ProviderError>
1034 where
1035 H: AsRef<FeltPrimitive> + Send + Sync,
1036 {
1037 self.send_request(
1038 JsonRpcMethod::TraceTransaction,
1039 TraceTransactionRequestRef {
1040 transaction_hash: transaction_hash.as_ref(),
1041 },
1042 )
1043 .await
1044 }
1045
1046 async fn simulate_transactions<B, TX, S>(
1053 &self,
1054 block_id: B,
1055 transactions: TX,
1056 simulation_flags: S,
1057 ) -> Result<Vec<SimulatedTransaction>, ProviderError>
1058 where
1059 B: AsRef<BlockId> + Send + Sync,
1060 TX: AsRef<[BroadcastedTransaction]> + Send + Sync,
1061 S: AsRef<[SimulationFlag]> + Send + Sync,
1062 {
1063 self.send_request(
1064 JsonRpcMethod::SimulateTransactions,
1065 SimulateTransactionsRequestRef {
1066 block_id: block_id.as_ref(),
1067 transactions: transactions.as_ref(),
1068 simulation_flags: simulation_flags.as_ref(),
1069 },
1070 )
1071 .await
1072 }
1073
1074 async fn trace_block_transactions<B>(
1076 &self,
1077 block_id: B,
1078 ) -> Result<Vec<TransactionTraceWithHash>, ProviderError>
1079 where
1080 B: AsRef<ConfirmedBlockId> + Send + Sync,
1081 {
1082 self.send_request(
1083 JsonRpcMethod::TraceBlockTransactions,
1084 TraceBlockTransactionsRequestRef {
1085 block_id: block_id.as_ref(),
1086 },
1087 )
1088 .await
1089 }
1090
1091 async fn batch_requests<R>(
1092 &self,
1093 requests: R,
1094 ) -> Result<Vec<ProviderResponseData>, ProviderError>
1095 where
1096 R: AsRef<[ProviderRequestData]> + Send + Sync,
1097 {
1098 self.send_requests(requests).await
1099 }
1100}
1101
1102impl ProviderRequestData {
1103 const fn jsonrpc_method(&self) -> JsonRpcMethod {
1104 match self {
1105 Self::SpecVersion(_) => JsonRpcMethod::SpecVersion,
1106 Self::GetBlockWithTxHashes(_) => JsonRpcMethod::GetBlockWithTxHashes,
1107 Self::GetBlockWithTxs(_) => JsonRpcMethod::GetBlockWithTxs,
1108 Self::GetBlockWithReceipts(_) => JsonRpcMethod::GetBlockWithReceipts,
1109 Self::GetStateUpdate(_) => JsonRpcMethod::GetStateUpdate,
1110 Self::GetStorageAt(_) => JsonRpcMethod::GetStorageAt,
1111 Self::GetMessagesStatus(_) => JsonRpcMethod::GetMessagesStatus,
1112 Self::GetTransactionStatus(_) => JsonRpcMethod::GetTransactionStatus,
1113 Self::GetTransactionByHash(_) => JsonRpcMethod::GetTransactionByHash,
1114 Self::GetTransactionByBlockIdAndIndex(_) => {
1115 JsonRpcMethod::GetTransactionByBlockIdAndIndex
1116 }
1117 Self::GetTransactionReceipt(_) => JsonRpcMethod::GetTransactionReceipt,
1118 Self::GetClass(_) => JsonRpcMethod::GetClass,
1119 Self::GetClassHashAt(_) => JsonRpcMethod::GetClassHashAt,
1120 Self::GetClassAt(_) => JsonRpcMethod::GetClassAt,
1121 Self::GetBlockTransactionCount(_) => JsonRpcMethod::GetBlockTransactionCount,
1122 Self::Call(_) => JsonRpcMethod::Call,
1123 Self::EstimateFee(_) => JsonRpcMethod::EstimateFee,
1124 Self::EstimateMessageFee(_) => JsonRpcMethod::EstimateMessageFee,
1125 Self::BlockNumber(_) => JsonRpcMethod::BlockNumber,
1126 Self::BlockHashAndNumber(_) => JsonRpcMethod::BlockHashAndNumber,
1127 Self::ChainId(_) => JsonRpcMethod::ChainId,
1128 Self::Syncing(_) => JsonRpcMethod::Syncing,
1129 Self::GetEvents(_) => JsonRpcMethod::GetEvents,
1130 Self::GetNonce(_) => JsonRpcMethod::GetNonce,
1131 Self::GetStorageProof(_) => JsonRpcMethod::GetStorageProof,
1132 Self::AddInvokeTransaction(_) => JsonRpcMethod::AddInvokeTransaction,
1133 Self::AddDeclareTransaction(_) => JsonRpcMethod::AddDeclareTransaction,
1134 Self::AddDeployAccountTransaction(_) => JsonRpcMethod::AddDeployAccountTransaction,
1135 Self::TraceTransaction(_) => JsonRpcMethod::TraceTransaction,
1136 Self::SimulateTransactions(_) => JsonRpcMethod::SimulateTransactions,
1137 Self::TraceBlockTransactions(_) => JsonRpcMethod::TraceBlockTransactions,
1138 Self::SubscribeNewHeads(_) => JsonRpcMethod::SubscribeNewHeads,
1139 Self::SubscribeEvents(_) => JsonRpcMethod::SubscribeEvents,
1140 Self::SubscribeTransactionStatus(_) => JsonRpcMethod::SubscribeTransactionStatus,
1141 Self::SubscribeNewTransactionReceipts(_) => {
1142 JsonRpcMethod::SubscribeNewTransactionReceipts
1143 }
1144 Self::SubscribeNewTransactions(_) => JsonRpcMethod::SubscribeNewTransactions,
1145 Self::Unsubscribe(_) => JsonRpcMethod::Unsubscribe,
1146 }
1147 }
1148}
1149
1150impl StreamUpdateData {
1151 const fn jsonrpc_method(&self) -> JsonRpcMethod {
1152 match self {
1153 Self::SubscriptionNewHeads(_) => JsonRpcMethod::SubscriptionNewHeads,
1154 Self::SubscriptionEvents(_) => JsonRpcMethod::SubscriptionEvents,
1155 Self::SubscriptionTransactionStatus(_) => JsonRpcMethod::SubscriptionTransactionStatus,
1156 Self::SubscriptionNewTransactionReceipts(_) => {
1157 JsonRpcMethod::SubscriptionNewTransactionReceipts
1158 }
1159 Self::SubscriptionNewTransaction(_) => JsonRpcMethod::SubscriptionNewTransaction,
1160 Self::SubscriptionReorg(_) => JsonRpcMethod::SubscriptionReorg,
1161 }
1162 }
1163}
1164
1165impl Serialize for JsonRpcRequest {
1166 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
1167 where
1168 S: serde::Serializer,
1169 {
1170 #[derive(Serialize)]
1171 struct RawRequest<'a> {
1172 jsonrpc: &'static str,
1173 id: u64,
1174 method: JsonRpcMethod,
1175 params: &'a ProviderRequestData,
1176 }
1177
1178 RawRequest::serialize(
1179 &RawRequest {
1180 jsonrpc: "2.0",
1181 id: self.id,
1182 method: self.data.jsonrpc_method(),
1183 params: &self.data,
1184 },
1185 serializer,
1186 )
1187 }
1188}
1189
1190impl<'de> Deserialize<'de> for JsonRpcRequest {
1191 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
1192 where
1193 D: serde::Deserializer<'de>,
1194 {
1195 #[derive(Deserialize)]
1196 struct RawRequest {
1197 id: u64,
1198 method: JsonRpcMethod,
1199 params: serde_json::Value,
1200 }
1201
1202 let error_mapper =
1203 |err| serde::de::Error::custom(format!("unable to decode params: {err}"));
1204
1205 let raw_request = RawRequest::deserialize(deserializer)?;
1206 let request_data = match raw_request.method {
1207 JsonRpcMethod::SpecVersion => ProviderRequestData::SpecVersion(
1208 serde_json::from_value::<SpecVersionRequest>(raw_request.params)
1209 .map_err(error_mapper)?,
1210 ),
1211 JsonRpcMethod::GetBlockWithTxHashes => ProviderRequestData::GetBlockWithTxHashes(
1212 serde_json::from_value::<GetBlockWithTxHashesRequest>(raw_request.params)
1213 .map_err(error_mapper)?,
1214 ),
1215 JsonRpcMethod::GetBlockWithTxs => ProviderRequestData::GetBlockWithTxs(
1216 serde_json::from_value::<GetBlockWithTxsRequest>(raw_request.params)
1217 .map_err(error_mapper)?,
1218 ),
1219 JsonRpcMethod::GetBlockWithReceipts => ProviderRequestData::GetBlockWithReceipts(
1220 serde_json::from_value::<GetBlockWithReceiptsRequest>(raw_request.params)
1221 .map_err(error_mapper)?,
1222 ),
1223 JsonRpcMethod::GetStateUpdate => ProviderRequestData::GetStateUpdate(
1224 serde_json::from_value::<GetStateUpdateRequest>(raw_request.params)
1225 .map_err(error_mapper)?,
1226 ),
1227 JsonRpcMethod::GetStorageAt => ProviderRequestData::GetStorageAt(
1228 serde_json::from_value::<GetStorageAtRequest>(raw_request.params)
1229 .map_err(error_mapper)?,
1230 ),
1231 JsonRpcMethod::GetMessagesStatus => ProviderRequestData::GetMessagesStatus(
1232 serde_json::from_value::<GetMessagesStatusRequest>(raw_request.params)
1233 .map_err(error_mapper)?,
1234 ),
1235 JsonRpcMethod::GetTransactionStatus => ProviderRequestData::GetTransactionStatus(
1236 serde_json::from_value::<GetTransactionStatusRequest>(raw_request.params)
1237 .map_err(error_mapper)?,
1238 ),
1239 JsonRpcMethod::GetTransactionByHash => ProviderRequestData::GetTransactionByHash(
1240 serde_json::from_value::<GetTransactionByHashRequest>(raw_request.params)
1241 .map_err(error_mapper)?,
1242 ),
1243 JsonRpcMethod::GetTransactionByBlockIdAndIndex => {
1244 ProviderRequestData::GetTransactionByBlockIdAndIndex(
1245 serde_json::from_value::<GetTransactionByBlockIdAndIndexRequest>(
1246 raw_request.params,
1247 )
1248 .map_err(error_mapper)?,
1249 )
1250 }
1251 JsonRpcMethod::GetTransactionReceipt => ProviderRequestData::GetTransactionReceipt(
1252 serde_json::from_value::<GetTransactionReceiptRequest>(raw_request.params)
1253 .map_err(error_mapper)?,
1254 ),
1255 JsonRpcMethod::GetClass => ProviderRequestData::GetClass(
1256 serde_json::from_value::<GetClassRequest>(raw_request.params)
1257 .map_err(error_mapper)?,
1258 ),
1259 JsonRpcMethod::GetClassHashAt => ProviderRequestData::GetClassHashAt(
1260 serde_json::from_value::<GetClassHashAtRequest>(raw_request.params)
1261 .map_err(error_mapper)?,
1262 ),
1263 JsonRpcMethod::GetClassAt => ProviderRequestData::GetClassAt(
1264 serde_json::from_value::<GetClassAtRequest>(raw_request.params)
1265 .map_err(error_mapper)?,
1266 ),
1267 JsonRpcMethod::GetBlockTransactionCount => {
1268 ProviderRequestData::GetBlockTransactionCount(
1269 serde_json::from_value::<GetBlockTransactionCountRequest>(raw_request.params)
1270 .map_err(error_mapper)?,
1271 )
1272 }
1273 JsonRpcMethod::Call => ProviderRequestData::Call(
1274 serde_json::from_value::<CallRequest>(raw_request.params).map_err(error_mapper)?,
1275 ),
1276 JsonRpcMethod::EstimateFee => ProviderRequestData::EstimateFee(
1277 serde_json::from_value::<EstimateFeeRequest>(raw_request.params)
1278 .map_err(error_mapper)?,
1279 ),
1280 JsonRpcMethod::EstimateMessageFee => ProviderRequestData::EstimateMessageFee(
1281 serde_json::from_value::<EstimateMessageFeeRequest>(raw_request.params)
1282 .map_err(error_mapper)?,
1283 ),
1284 JsonRpcMethod::BlockNumber => ProviderRequestData::BlockNumber(
1285 serde_json::from_value::<BlockNumberRequest>(raw_request.params)
1286 .map_err(error_mapper)?,
1287 ),
1288 JsonRpcMethod::BlockHashAndNumber => ProviderRequestData::BlockHashAndNumber(
1289 serde_json::from_value::<BlockHashAndNumberRequest>(raw_request.params)
1290 .map_err(error_mapper)?,
1291 ),
1292 JsonRpcMethod::ChainId => ProviderRequestData::ChainId(
1293 serde_json::from_value::<ChainIdRequest>(raw_request.params)
1294 .map_err(error_mapper)?,
1295 ),
1296 JsonRpcMethod::Syncing => ProviderRequestData::Syncing(
1297 serde_json::from_value::<SyncingRequest>(raw_request.params)
1298 .map_err(error_mapper)?,
1299 ),
1300 JsonRpcMethod::GetEvents => ProviderRequestData::GetEvents(
1301 serde_json::from_value::<GetEventsRequest>(raw_request.params)
1302 .map_err(error_mapper)?,
1303 ),
1304 JsonRpcMethod::GetNonce => ProviderRequestData::GetNonce(
1305 serde_json::from_value::<GetNonceRequest>(raw_request.params)
1306 .map_err(error_mapper)?,
1307 ),
1308 JsonRpcMethod::GetStorageProof => ProviderRequestData::GetStorageProof(
1309 serde_json::from_value::<GetStorageProofRequest>(raw_request.params)
1310 .map_err(error_mapper)?,
1311 ),
1312 JsonRpcMethod::AddInvokeTransaction => ProviderRequestData::AddInvokeTransaction(
1313 serde_json::from_value::<AddInvokeTransactionRequest>(raw_request.params)
1314 .map_err(error_mapper)?,
1315 ),
1316 JsonRpcMethod::AddDeclareTransaction => ProviderRequestData::AddDeclareTransaction(
1317 serde_json::from_value::<AddDeclareTransactionRequest>(raw_request.params)
1318 .map_err(error_mapper)?,
1319 ),
1320 JsonRpcMethod::AddDeployAccountTransaction => {
1321 ProviderRequestData::AddDeployAccountTransaction(
1322 serde_json::from_value::<AddDeployAccountTransactionRequest>(
1323 raw_request.params,
1324 )
1325 .map_err(error_mapper)?,
1326 )
1327 }
1328 JsonRpcMethod::TraceTransaction => ProviderRequestData::TraceTransaction(
1329 serde_json::from_value::<TraceTransactionRequest>(raw_request.params)
1330 .map_err(error_mapper)?,
1331 ),
1332 JsonRpcMethod::SimulateTransactions => ProviderRequestData::SimulateTransactions(
1333 serde_json::from_value::<SimulateTransactionsRequest>(raw_request.params)
1334 .map_err(error_mapper)?,
1335 ),
1336 JsonRpcMethod::TraceBlockTransactions => ProviderRequestData::TraceBlockTransactions(
1337 serde_json::from_value::<TraceBlockTransactionsRequest>(raw_request.params)
1338 .map_err(error_mapper)?,
1339 ),
1340 JsonRpcMethod::SubscribeNewHeads => ProviderRequestData::SubscribeNewHeads(
1341 serde_json::from_value::<SubscribeNewHeadsRequest>(raw_request.params)
1342 .map_err(error_mapper)?,
1343 ),
1344 JsonRpcMethod::SubscribeEvents => ProviderRequestData::SubscribeEvents(
1345 serde_json::from_value::<SubscribeEventsRequest>(raw_request.params)
1346 .map_err(error_mapper)?,
1347 ),
1348 JsonRpcMethod::SubscribeTransactionStatus => {
1349 ProviderRequestData::SubscribeTransactionStatus(
1350 serde_json::from_value::<SubscribeTransactionStatusRequest>(raw_request.params)
1351 .map_err(error_mapper)?,
1352 )
1353 }
1354 JsonRpcMethod::SubscribeNewTransactionReceipts => {
1355 ProviderRequestData::SubscribeNewTransactionReceipts(
1356 serde_json::from_value::<SubscribeNewTransactionReceiptsRequest>(
1357 raw_request.params,
1358 )
1359 .map_err(error_mapper)?,
1360 )
1361 }
1362 JsonRpcMethod::SubscribeNewTransactions => {
1363 ProviderRequestData::SubscribeNewTransactions(
1364 serde_json::from_value::<SubscribeNewTransactionsRequest>(raw_request.params)
1365 .map_err(error_mapper)?,
1366 )
1367 }
1368 JsonRpcMethod::Unsubscribe => ProviderRequestData::Unsubscribe(
1369 serde_json::from_value::<UnsubscribeRequest>(raw_request.params)
1370 .map_err(error_mapper)?,
1371 ),
1372 JsonRpcMethod::SubscriptionNewHeads
1373 | JsonRpcMethod::SubscriptionEvents
1374 | JsonRpcMethod::SubscriptionTransactionStatus
1375 | JsonRpcMethod::SubscriptionNewTransactionReceipts
1376 | JsonRpcMethod::SubscriptionNewTransaction
1377 | JsonRpcMethod::SubscriptionReorg => {
1378 return Err(serde::de::Error::custom(format!(
1379 "unsupported request method: {:?}",
1380 raw_request.method
1381 )))
1382 }
1383 };
1384
1385 Ok(Self {
1386 id: raw_request.id,
1387 data: request_data,
1388 })
1389 }
1390}
1391
1392impl Serialize for JsonRpcStreamUpdate {
1393 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
1394 where
1395 S: serde::Serializer,
1396 {
1397 #[derive(Serialize)]
1398 struct RawRequest<'a> {
1399 jsonrpc: &'static str,
1400 method: JsonRpcMethod,
1401 params: &'a StreamUpdateData,
1402 }
1403
1404 RawRequest::serialize(
1405 &RawRequest {
1406 jsonrpc: "2.0",
1407 method: self.data.jsonrpc_method(),
1408 params: &self.data,
1409 },
1410 serializer,
1411 )
1412 }
1413}
1414
1415impl<'de> Deserialize<'de> for JsonRpcStreamUpdate {
1416 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
1417 where
1418 D: serde::Deserializer<'de>,
1419 {
1420 #[derive(Deserialize)]
1421 struct RawRequest {
1422 method: JsonRpcMethod,
1423 params: serde_json::Value,
1424 }
1425
1426 let error_mapper =
1427 |err| serde::de::Error::custom(format!("unable to decode params: {err}"));
1428
1429 let raw_request = RawRequest::deserialize(deserializer)?;
1430 let request_data = match raw_request.method {
1431 JsonRpcMethod::SubscriptionNewHeads => StreamUpdateData::SubscriptionNewHeads(
1432 serde_json::from_value::<SubscriptionNewHeadsRequest>(raw_request.params)
1433 .map_err(error_mapper)?,
1434 ),
1435 JsonRpcMethod::SubscriptionEvents => StreamUpdateData::SubscriptionEvents(
1436 serde_json::from_value::<SubscriptionEventsRequest>(raw_request.params)
1437 .map_err(error_mapper)?,
1438 ),
1439 JsonRpcMethod::SubscriptionTransactionStatus => {
1440 StreamUpdateData::SubscriptionTransactionStatus(
1441 serde_json::from_value::<SubscriptionTransactionStatusRequest>(
1442 raw_request.params,
1443 )
1444 .map_err(error_mapper)?,
1445 )
1446 }
1447 JsonRpcMethod::SubscriptionNewTransactionReceipts => {
1448 StreamUpdateData::SubscriptionNewTransactionReceipts(
1449 serde_json::from_value::<SubscriptionNewTransactionReceiptsRequest>(
1450 raw_request.params,
1451 )
1452 .map_err(error_mapper)?,
1453 )
1454 }
1455 JsonRpcMethod::SubscriptionNewTransaction => {
1456 StreamUpdateData::SubscriptionNewTransaction(
1457 serde_json::from_value::<SubscriptionNewTransactionRequest>(raw_request.params)
1458 .map_err(error_mapper)?,
1459 )
1460 }
1461 JsonRpcMethod::SubscriptionReorg => StreamUpdateData::SubscriptionReorg(
1462 serde_json::from_value::<SubscriptionReorgRequest>(raw_request.params)
1463 .map_err(error_mapper)?,
1464 ),
1465 JsonRpcMethod::SpecVersion
1466 | JsonRpcMethod::GetBlockWithTxHashes
1467 | JsonRpcMethod::GetBlockWithTxs
1468 | JsonRpcMethod::GetBlockWithReceipts
1469 | JsonRpcMethod::GetStateUpdate
1470 | JsonRpcMethod::GetStorageAt
1471 | JsonRpcMethod::GetMessagesStatus
1472 | JsonRpcMethod::GetTransactionStatus
1473 | JsonRpcMethod::GetTransactionByHash
1474 | JsonRpcMethod::GetTransactionByBlockIdAndIndex
1475 | JsonRpcMethod::GetTransactionReceipt
1476 | JsonRpcMethod::GetClass
1477 | JsonRpcMethod::GetClassHashAt
1478 | JsonRpcMethod::GetClassAt
1479 | JsonRpcMethod::GetBlockTransactionCount
1480 | JsonRpcMethod::Call
1481 | JsonRpcMethod::EstimateFee
1482 | JsonRpcMethod::EstimateMessageFee
1483 | JsonRpcMethod::BlockNumber
1484 | JsonRpcMethod::BlockHashAndNumber
1485 | JsonRpcMethod::ChainId
1486 | JsonRpcMethod::Syncing
1487 | JsonRpcMethod::GetEvents
1488 | JsonRpcMethod::GetNonce
1489 | JsonRpcMethod::GetStorageProof
1490 | JsonRpcMethod::AddInvokeTransaction
1491 | JsonRpcMethod::AddDeclareTransaction
1492 | JsonRpcMethod::AddDeployAccountTransaction
1493 | JsonRpcMethod::TraceTransaction
1494 | JsonRpcMethod::SimulateTransactions
1495 | JsonRpcMethod::TraceBlockTransactions
1496 | JsonRpcMethod::SubscribeNewHeads
1497 | JsonRpcMethod::SubscribeEvents
1498 | JsonRpcMethod::SubscribeTransactionStatus
1499 | JsonRpcMethod::SubscribeNewTransactionReceipts
1500 | JsonRpcMethod::SubscribeNewTransactions
1501 | JsonRpcMethod::Unsubscribe => {
1502 return Err(serde::de::Error::custom(format!(
1503 "unsupported request method: {:?}",
1504 raw_request.method
1505 )))
1506 }
1507 };
1508
1509 Ok(Self { data: request_data })
1510 }
1511}
1512
1513impl<T> ProviderImplError for JsonRpcClientError<T>
1514where
1515 T: 'static + Error + Send + Sync,
1516{
1517 fn as_any(&self) -> &dyn Any {
1518 self
1519 }
1520}
1521
1522impl<T> From<JsonRpcClientError<T>> for ProviderError
1523where
1524 T: 'static + Error + Send + Sync,
1525{
1526 fn from(value: JsonRpcClientError<T>) -> Self {
1527 Self::Other(Box::new(value))
1528 }
1529}
1530
1531impl<T> From<serde_json::Error> for JsonRpcClientError<T> {
1532 fn from(value: serde_json::Error) -> Self {
1533 Self::JsonError(value)
1534 }
1535}
1536
1537impl TryFrom<&JsonRpcError> for StarknetError {
1538 type Error = JsonRpcErrorConversionError;
1539
1540 fn try_from(value: &JsonRpcError) -> Result<Self, Self::Error> {
1541 match value.code {
1542 1 => Ok(Self::FailedToReceiveTransaction),
1543 20 => Ok(Self::ContractNotFound),
1544 21 => Ok(Self::EntrypointNotFound),
1545 24 => Ok(Self::BlockNotFound),
1546 27 => Ok(Self::InvalidTransactionIndex),
1547 28 => Ok(Self::ClassHashNotFound),
1548 29 => Ok(Self::TransactionHashNotFound),
1549 31 => Ok(Self::PageSizeTooBig),
1550 32 => Ok(Self::NoBlocks),
1551 33 => Ok(Self::InvalidContinuationToken),
1552 34 => Ok(Self::TooManyKeysInFilter),
1553 40 => {
1554 let data = ContractErrorData::deserialize(
1555 value
1556 .data
1557 .as_ref()
1558 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1559 )
1560 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1561 Ok(Self::ContractError(data))
1562 }
1563 41 => {
1564 let data = TransactionExecutionErrorData::deserialize(
1565 value
1566 .data
1567 .as_ref()
1568 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1569 )
1570 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1571 Ok(Self::TransactionExecutionError(data))
1572 }
1573 51 => Ok(Self::ClassAlreadyDeclared),
1574 52 => {
1575 let data = String::deserialize(
1576 value
1577 .data
1578 .as_ref()
1579 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1580 )
1581 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1582 Ok(Self::InvalidTransactionNonce(data))
1583 }
1584 53 => Ok(Self::InsufficientResourcesForValidate),
1585 54 => Ok(Self::InsufficientAccountBalance),
1586 55 => {
1587 let data = String::deserialize(
1588 value
1589 .data
1590 .as_ref()
1591 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1592 )
1593 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1594 Ok(Self::ValidationFailure(data))
1595 }
1596 56 => {
1597 let data = String::deserialize(
1598 value
1599 .data
1600 .as_ref()
1601 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1602 )
1603 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1604 Ok(Self::CompilationFailed(data))
1605 }
1606 57 => Ok(Self::ContractClassSizeIsTooLarge),
1607 58 => Ok(Self::NonAccount),
1608 59 => Ok(Self::DuplicateTx),
1609 60 => Ok(Self::CompiledClassHashMismatch),
1610 61 => Ok(Self::UnsupportedTxVersion),
1611 62 => Ok(Self::UnsupportedContractClassVersion),
1612 63 => {
1613 let data = String::deserialize(
1614 value
1615 .data
1616 .as_ref()
1617 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1618 )
1619 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1620 Ok(Self::UnexpectedError(data))
1621 }
1622 64 => Ok(Self::ReplacementTransactionUnderpriced),
1623 65 => Ok(Self::FeeBelowMinimum),
1624 66 => Ok(Self::InvalidSubscriptionId),
1625 67 => Ok(Self::TooManyAddressesInFilter),
1626 68 => Ok(Self::TooManyBlocksBack),
1627 10 => {
1628 let data = NoTraceAvailableErrorData::deserialize(
1629 value
1630 .data
1631 .as_ref()
1632 .ok_or(JsonRpcErrorConversionError::MissingData)?,
1633 )
1634 .map_err(|_| JsonRpcErrorConversionError::DataParsingFailure)?;
1635 Ok(Self::NoTraceAvailable(data))
1636 }
1637 _ => Err(JsonRpcErrorConversionError::UnknownCode),
1638 }
1639 }
1640}
1641
1642impl Error for JsonRpcError {}
1643
1644impl Display for JsonRpcError {
1645 fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
1646 match &self.data {
1647 Some(data) => {
1648 write!(
1649 f,
1650 "JSON-RPC error: code={}, message=\"{}\", data={}",
1651 self.code,
1652 self.message,
1653 serde_json::to_string(data).map_err(|_| std::fmt::Error)?
1654 )
1655 }
1656 None => {
1657 write!(
1658 f,
1659 "JSON-RPC error: code={}, message=\"{}\"",
1660 self.code, self.message
1661 )
1662 }
1663 }
1664 }
1665}