near_api/common/query/
block_rpc.rs

1use near_api_types::Reference;
2use near_openapi_client::types::{
3    BlockId, ErrorWrapperForRpcBlockError, Finality, JsonRpcRequestForBlock,
4    JsonRpcRequestForBlockMethod, JsonRpcResponseForRpcBlockResponseAndRpcBlockError,
5    RpcBlockError, RpcBlockRequest, RpcBlockResponse,
6};
7use near_openapi_client::Client;
8
9use crate::common::utils::to_retry_error;
10use crate::{
11    advanced::RpcType, common::utils::is_critical_blocks_error, config::RetryResponse,
12    errors::SendRequestError, NetworkConfig,
13};
14
15#[derive(Clone, Debug)]
16pub struct SimpleBlockRpc;
17
18#[async_trait::async_trait]
19impl RpcType for SimpleBlockRpc {
20    type RpcReference = Reference;
21    type Response = RpcBlockResponse;
22    type Error = RpcBlockError;
23    async fn send_query(
24        &self,
25        client: &Client,
26        _network: &NetworkConfig,
27        reference: &Reference,
28    ) -> RetryResponse<RpcBlockResponse, SendRequestError<RpcBlockError>> {
29        let request = match reference {
30            Reference::Optimistic => RpcBlockRequest::Finality(Finality::Optimistic),
31            Reference::NearFinal => RpcBlockRequest::Finality(Finality::NearFinal),
32            Reference::Final => RpcBlockRequest::Finality(Finality::Final),
33            Reference::AtBlock(block) => RpcBlockRequest::BlockId(BlockId::BlockHeight(*block)),
34            Reference::AtBlockHash(block_hash) => {
35                RpcBlockRequest::BlockId(BlockId::CryptoHash((*block_hash).into()))
36            }
37        };
38        let response = client
39            .block(&JsonRpcRequestForBlock {
40                id: "0".to_string(),
41                jsonrpc: "2.0".to_string(),
42                method: JsonRpcRequestForBlockMethod::Block,
43                params: request,
44            })
45            .await
46            .map(|r| r.into_inner())
47            .map_err(SendRequestError::from);
48
49        match response {
50            Ok(JsonRpcResponseForRpcBlockResponseAndRpcBlockError::Variant0 { result, .. }) => {
51                RetryResponse::Ok(result)
52            }
53            Ok(JsonRpcResponseForRpcBlockResponseAndRpcBlockError::Variant1 { error, .. }) => {
54                let error = SendRequestError::from(error);
55                to_retry_error(error, is_critical_blocks_error)
56            }
57            Err(err) => to_retry_error(err, is_critical_blocks_error),
58        }
59    }
60}
61
62impl From<ErrorWrapperForRpcBlockError> for SendRequestError<RpcBlockError> {
63    fn from(err: ErrorWrapperForRpcBlockError) -> Self {
64        match err {
65            ErrorWrapperForRpcBlockError::InternalError(internal_error) => {
66                Self::InternalError(internal_error)
67            }
68            ErrorWrapperForRpcBlockError::RequestValidationError(
69                rpc_request_validation_error_kind,
70            ) => Self::RequestValidationError(rpc_request_validation_error_kind),
71            ErrorWrapperForRpcBlockError::HandlerError(server_error) => {
72                Self::ServerError(server_error)
73            }
74        }
75    }
76}