diff --git a/book/src/api-reference/jsonrpc-api.md b/book/src/api-reference/jsonrpc-api.md index bdd9ffcdc2..8345be3903 100644 --- a/book/src/api-reference/jsonrpc-api.md +++ b/book/src/api-reference/jsonrpc-api.md @@ -96,6 +96,13 @@ If commitment configuration is not provided, the node will default to `"commitme Only methods that query bank state accept the commitment parameter. They are indicated in the API Reference below. +#### RpcResponse Structure +Many methods that take a commitment parameter return an RpcResponse JSON object comprised of two parts: + +* `context` : An RpcResponseContext JSON structure including a `slot` field at which the operation was evaluated. +* `value` : The value returned by the operation itself. + + ## JSON RPC API Reference ### confirmTransaction @@ -109,7 +116,7 @@ Returns a transaction receipt #### Results: -* `boolean` - Transaction status, true if Transaction is confirmed +* `RpcResponse` - RpcResponse JSON object with `value` field set to Transaction status, boolean true if Transaction is confirmed #### Example: @@ -118,7 +125,7 @@ Returns a transaction receipt curl -X POST -H "Content-Type: application/json" -d '{"jsonrpc":"2.0", "id":1, "method":"confirmTransaction", "params":["5VERv8NMvzbJMEkV8xnrLkEaWRtSz9CosKDYjCJjBRnbJLgp8uirBgmQpjKhoR4tjF3ZpRzrFmBV6UjKdiSZkQUW"]}' http://localhost:8899 // Result -{"jsonrpc":"2.0","result":true,"id":1} +{"jsonrpc":"2.0","result":{"context":{"slot":1},"value":true},"id":1} ``` ### getAccountInfo @@ -132,8 +139,9 @@ Returns all information associated with the account of provided Pubkey #### Results: -The result field will be a JSON object with the following sub fields: +The result value will be an RpcResponse JSON object containing an AccountInfo JSON object. +* `RpcResponse`, RpcResponse JSON object with `value` field set to AccountInfo, a JSON object containing: * `lamports`, number of lamports assigned to this account, as a signed 64-bit integer * `owner`, array of 32 bytes representing the program this account has been assigned to * `data`, array of bytes representing any data associated with the account @@ -146,7 +154,7 @@ The result field will be a JSON object with the following sub fields: curl -X POST -H "Content-Type: application/json" -d '{"jsonrpc":"2.0", "id":1, "method":"getAccountInfo", "params":["2gVkYWexTHR5Hb2aLeQN3tnngvWzisFKXDUPrgMHpdST"]}' http://localhost:8899 // Result -{"jsonrpc":"2.0","result":{"executable":false,"owner":[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],"lamports":1,"data":[3,0,0,0,0,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0.21.0,0,0,0,0,0,0,50,48,53,48,45,48,49,45,48,49,84,48,48,58,48,48,58,48,48,90,252,10,7,28,246,140,88,177,98,82,10,227,89,81,18,30,194,101,199,16,11,73,133,20,246,62,114,39,20,113,189,32,50,0,0,0,0,0,0,0,247,15,36,102,167,83,225,42,133,127,82,34,36,224,207,130,109,230,224,188,163,33,213,13,5,117,211,251,65,159,197,51,0,0,0,0,0,0]},"id":1} +{"jsonrpc":"2.0","result":{"context":{"slot":1},"value":{"executable":false,"owner":[1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0],"lamports":1,"data":[3,0,0,0,0,0,0,0,1,0,0,0,0,0,1,0,0,0,0,0,0,0.21.0,0,0,0,0,0,0,50,48,53,48,45,48,49,45,48,49,84,48,48,58,48,48,58,48,48,90,252,10,7,28,246,140,88,177,98,82,10,227,89,81,18,30,194,101,199,16,11,73,133,20,246,62,114,39,20,113,189,32,50,0,0,0,0,0,0,0,247,15,36,102,167,83,225,42,133,127,82,34,36,224,207,130,109,230,224,188,163,33,213,13,5,117,211,251,65,159,197,51,0,0,0,0,0,0]}},"id":1} ``` ### getBalance @@ -160,7 +168,7 @@ Returns the balance of the account of provided Pubkey #### Results: -* `integer` - quantity, as a signed 64-bit integer +* `RpcResponse` - RpcResponse JSON object with `value` field set to quantity, as a signed 64-bit integer #### Example: @@ -169,7 +177,7 @@ Returns the balance of the account of provided Pubkey curl -X POST -H "Content-Type: application/json" -d '{"jsonrpc":"2.0", "id":1, "method":"getBalance", "params":["83astBRguLMdt2h5U1Tpdq5tjFoJ6noeGwaY3mDLVcri"]}' http://localhost:8899 // Result -{"jsonrpc":"2.0","result":0,"id":1} +{"jsonrpc":"2.0","result":{"context":{"slot":1},"value":0},"id":1} ``` ### getBlockCommitment @@ -410,8 +418,9 @@ Returns a recent block hash from the ledger, and a fee schedule that can be used #### Results: -An array consisting of +An RpcResponse containing an array consisting of a string blockhash and FeeCalculator JSON object. +* `RpcResponse` - RpcResponse JSON object with `value` field set to an array including: * `string` - a Hash as base-58 encoded string * `FeeCalculator object` - the fee schedule for this block hash @@ -422,7 +431,7 @@ An array consisting of curl -X POST -H "Content-Type: application/json" -d '{"jsonrpc":"2.0","id":1, "method":"getRecentBlockhash"}' http://localhost:8899 // Result -{"jsonrpc":"2.0","result":["GH7ome3EiwEr7tu9JuTh2dpYWBJK3z69Xm1ZE3MEE6JC",{"lamportsPerSignature": 0}],"id":1} +{"jsonrpc":"2.0","result":{"context":{"slot":1},"value":["GH7ome3EiwEr7tu9JuTh2dpYWBJK3z69Xm1ZE3MEE6JC",{"lamportsPerSignature": 0}]},"id":1} ``` ### getSignatureStatus diff --git a/cli/tests/deploy.rs b/cli/tests/deploy.rs index 31f5c414d6..07e451fa8e 100644 --- a/cli/tests/deploy.rs +++ b/cli/tests/deploy.rs @@ -3,7 +3,7 @@ use solana_cli::cli::{process_command, CliCommand, CliConfig}; use solana_client::rpc_client::RpcClient; use solana_core::validator::new_validator_for_tests; use solana_drone::drone::run_local_drone; -use solana_sdk::{bpf_loader, commitment_config::CommitmentConfig, pubkey::Pubkey}; +use solana_sdk::{bpf_loader, pubkey::Pubkey}; use std::{ fs::{remove_dir_all, File}, io::Read, @@ -59,10 +59,7 @@ fn test_cli_deploy_program() { .as_str() .unwrap(); let program_id = Pubkey::from_str(&program_id_str).unwrap(); - - let account = rpc_client - .get_account_with_commitment(&program_id, CommitmentConfig::recent()) - .unwrap(); + let account = rpc_client.get_account(&program_id).unwrap(); assert_eq!(account.lamports, minimum_balance_for_rent_exemption); assert_eq!(account.owner, bpf_loader::id()); assert_eq!(account.executable, true); diff --git a/client/src/mock_rpc_client_request.rs b/client/src/mock_rpc_client_request.rs index 38019e9c58..a29e7c2736 100644 --- a/client/src/mock_rpc_client_request.rs +++ b/client/src/mock_rpc_client_request.rs @@ -1,3 +1,4 @@ +use crate::rpc_request::{Response, RpcResponseContext}; use crate::{ client_error::ClientError, generic_rpc_client_request::GenericRpcClientRequest, rpc_request::RpcRequest, @@ -48,12 +49,18 @@ impl GenericRpcClientRequest for MockRpcClientRequest { } RpcRequest::GetBalance => { let n = if self.url == "airdrop" { 0 } else { 50 }; - Value::Number(Number::from(n)) + serde_json::to_value(Response { + context: RpcResponseContext { slot: 1 }, + value: Value::Number(Number::from(n)), + })? } - RpcRequest::GetRecentBlockhash => Value::Array(vec![ - Value::String(PUBKEY.to_string()), - serde_json::to_value(FeeCalculator::default()).unwrap(), - ]), + RpcRequest::GetRecentBlockhash => serde_json::to_value(Response { + context: RpcResponseContext { slot: 1 }, + value: ( + Value::String(PUBKEY.to_string()), + serde_json::to_value(FeeCalculator::default()).unwrap(), + ), + })?, RpcRequest::GetSignatureStatus => { let response: Option> = if self.url == "account_in_use" { Some(Err(TransactionError::AccountInUse)) diff --git a/client/src/rpc_client.rs b/client/src/rpc_client.rs index 946965d55c..60163f21b7 100644 --- a/client/src/rpc_client.rs +++ b/client/src/rpc_client.rs @@ -1,3 +1,4 @@ +use crate::rpc_request::{Response, RpcResponse}; use crate::{ client_error::ClientError, generic_rpc_client_request::GenericRpcClientRequest, @@ -55,31 +56,39 @@ impl RpcClient { } } - pub fn confirm_transaction(&self, signature: &str) -> Result { - self.confirm_transaction_with_commitment(signature, CommitmentConfig::default()) + pub fn confirm_transaction(&self, signature: &str) -> io::Result { + Ok(self + .confirm_transaction_with_commitment(signature, CommitmentConfig::default())? + .value) } pub fn confirm_transaction_with_commitment( &self, signature: &str, commitment_config: CommitmentConfig, - ) -> Result { + ) -> RpcResponse { let params = json!(signature); - let response = self.client.send( - &RpcRequest::ConfirmTransaction, - Some(params), - 0, - Some(commitment_config), - )?; - if response.as_bool().is_none() { - Err(io::Error::new( - io::ErrorKind::Other, - "Received result of an unexpected type", + let response = self + .client + .send( + &RpcRequest::ConfirmTransaction, + Some(params), + 0, + Some(commitment_config), ) - .into()) - } else { - Ok(response.as_bool().unwrap()) - } + .map_err(|err| { + io::Error::new( + io::ErrorKind::Other, + format!("ConfirmTransaction request failure {:?}", err), + ) + })?; + + serde_json::from_value::>(response).map_err(|err| { + io::Error::new( + io::ErrorKind::Other, + format!("Received result of an unexpected type {:?}", err), + ) + }) } pub fn send_transaction(&self, transaction: &Transaction) -> Result { @@ -378,46 +387,69 @@ impl RpcClient { retries: usize, ) -> Result, Box> { let params = json!(format!("{}", pubkey)); - let res = self + let balance_json = self .client - .send(&RpcRequest::GetBalance, Some(params), retries, None)? - .as_u64(); - Ok(res) + .send(&RpcRequest::GetBalance, Some(params), retries, None) + .map_err(|err| { + io::Error::new( + io::ErrorKind::Other, + format!("RetryGetBalance request failure: {:?}", err), + ) + })?; + + Ok(Some( + serde_json::from_value::>(balance_json) + .map_err(|err| { + io::Error::new( + io::ErrorKind::Other, + format!("RetryGetBalance parse failure: {:?}", err), + ) + })? + .value, + )) } pub fn get_account(&self, pubkey: &Pubkey) -> io::Result { - self.get_account_with_commitment(pubkey, CommitmentConfig::default()) + Ok(self + .get_account_with_commitment(pubkey, CommitmentConfig::default()) + .map(|x| x.value.unwrap())?) } pub fn get_account_with_commitment( &self, pubkey: &Pubkey, commitment_config: CommitmentConfig, - ) -> io::Result { + ) -> RpcResponse> { let params = json!(format!("{}", pubkey)); let response = self.client.send( &RpcRequest::GetAccountInfo, Some(params), 0, - commitment_config.ok(), + Some(commitment_config), ); response - .and_then(|account_json| { - let account: Account = serde_json::from_value(account_json)?; - trace!("Response account {:?} {:?}", pubkey, account); - Ok(account) + .map(|result_json| { + if result_json.is_null() { + return Err(io::Error::new( + io::ErrorKind::Other, + format!("AccountNotFound: pubkey={}", pubkey), + )); + } + let result = serde_json::from_value::>>(result_json)?; + trace!("Response account {:?} {:?}", pubkey, result); + Ok(result) }) .map_err(|err| { io::Error::new( io::ErrorKind::Other, format!("AccountNotFound: pubkey={}: {}", pubkey, err), ) - }) + })? } pub fn get_account_data(&self, pubkey: &Pubkey) -> io::Result> { - self.get_account(pubkey).map(|account| account.data) + Ok(self.get_account(pubkey).unwrap().data) } pub fn get_minimum_balance_for_rent_exemption(&self, data_len: usize) -> io::Result { @@ -456,14 +488,16 @@ impl RpcClient { /// Request the balance of the account `pubkey`. pub fn get_balance(&self, pubkey: &Pubkey) -> io::Result { - self.get_balance_with_commitment(pubkey, CommitmentConfig::default()) + Ok(self + .get_balance_with_commitment(pubkey, CommitmentConfig::default())? + .value) } pub fn get_balance_with_commitment( &self, pubkey: &Pubkey, commitment_config: CommitmentConfig, - ) -> io::Result { + ) -> RpcResponse { let params = json!(pubkey.to_string()); let balance_json = self .client @@ -479,7 +513,8 @@ impl RpcClient { format!("GetBalance request failure: {:?}", err), ) })?; - serde_json::from_value(balance_json).map_err(|err| { + + serde_json::from_value::>(balance_json).map_err(|err| { io::Error::new( io::ErrorKind::Other, format!("GetBalance parse failure: {:?}", err), @@ -553,13 +588,15 @@ impl RpcClient { } pub fn get_recent_blockhash(&self) -> io::Result<(Hash, FeeCalculator)> { - self.get_recent_blockhash_with_commitment(CommitmentConfig::default()) + Ok(self + .get_recent_blockhash_with_commitment(CommitmentConfig::default())? + .value) } pub fn get_recent_blockhash_with_commitment( &self, commitment_config: CommitmentConfig, - ) -> io::Result<(Hash, FeeCalculator)> { + ) -> RpcResponse<(Hash, FeeCalculator)> { let response = self .client .send( @@ -575,21 +612,27 @@ impl RpcClient { ) })?; - let (blockhash, fee_calculator) = - serde_json::from_value::<(String, FeeCalculator)>(response).map_err(|err| { + let Response { + context, + value: (blockhash_str, fee_calculator), + } = serde_json::from_value::>(response).map_err( + |err| { io::Error::new( io::ErrorKind::Other, format!("GetRecentBlockhash parse failure: {:?}", err), ) - })?; - - let blockhash = blockhash.parse().map_err(|err| { + }, + )?; + let blockhash = blockhash_str.parse().map_err(|err| { io::Error::new( io::ErrorKind::Other, format!("GetRecentBlockhash hash parse failure: {:?}", err), ) })?; - Ok((blockhash, fee_calculator)) + Ok(Response { + context, + value: (blockhash, fee_calculator), + }) } pub fn get_new_blockhash(&self, blockhash: &Hash) -> io::Result<(Hash, FeeCalculator)> { @@ -658,7 +701,7 @@ impl RpcClient { loop { match self.get_balance_with_commitment(&pubkey, commitment_config.clone()) { Ok(bal) => { - return Ok(bal); + return Ok(bal.value); } Err(e) => { sleep(*polling_frequency); diff --git a/client/src/rpc_request.rs b/client/src/rpc_request.rs index 8e2a64cb79..e1c3dc7866 100644 --- a/client/src/rpc_request.rs +++ b/client/src/rpc_request.rs @@ -1,9 +1,24 @@ +use jsonrpc_core::Result as JsonResult; use serde_json::{json, Value}; use solana_sdk::{ clock::{Epoch, Slot}, commitment_config::CommitmentConfig, }; -use std::{error, fmt}; +use std::{error, fmt, io}; + +pub type RpcResponseIn = JsonResult>; +pub type RpcResponse = io::Result>; + +#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)] +pub struct RpcResponseContext { + pub slot: u64, +} + +#[derive(Debug, Clone, PartialEq, Serialize, Deserialize)] +pub struct Response { + pub context: RpcResponseContext, + pub value: T, +} #[derive(Serialize, Deserialize, Clone, Debug)] #[serde(rename_all = "camelCase")] diff --git a/client/src/thin_client.rs b/client/src/thin_client.rs index 0c557501dc..3bad655d8e 100644 --- a/client/src/thin_client.rs +++ b/client/src/thin_client.rs @@ -4,6 +4,7 @@ //! unstable and may change in future releases. use crate::rpc_client::RpcClient; +use crate::rpc_request::Response; use bincode::{serialize_into, serialized_size}; use log::*; use solana_sdk::{ @@ -383,7 +384,11 @@ impl SyncClient for ThinClient { } fn get_account(&self, pubkey: &Pubkey) -> TransportResult> { - Ok(self.rpc_client().get_account(pubkey).ok()) + let account = self.rpc_client().get_account(pubkey); + match account { + Ok(value) => Ok(Some(value)), + Err(_) => Ok(None), + } } fn get_account_with_commitment( @@ -393,13 +398,12 @@ impl SyncClient for ThinClient { ) -> TransportResult> { Ok(self .rpc_client() - .get_account_with_commitment(pubkey, commitment_config) - .ok()) + .get_account_with_commitment(pubkey, commitment_config)? + .value) } fn get_balance(&self, pubkey: &Pubkey) -> TransportResult { - let balance = self.rpc_client().get_balance(pubkey)?; - Ok(balance) + Ok(self.rpc_client().get_balance(pubkey)?) } fn get_balance_with_commitment( @@ -410,7 +414,7 @@ impl SyncClient for ThinClient { let balance = self .rpc_client() .get_balance_with_commitment(pubkey, commitment_config)?; - Ok(balance) + Ok(balance.value) } fn get_recent_blockhash(&self) -> TransportResult<(Hash, FeeCalculator)> { @@ -426,9 +430,9 @@ impl SyncClient for ThinClient { let recent_blockhash = self.rpc_clients[index].get_recent_blockhash_with_commitment(commitment_config); match recent_blockhash { - Ok(recent_blockhash) => { + Ok(Response { value, .. }) => { self.optimizer.report(index, duration_as_ms(&now.elapsed())); - Ok(recent_blockhash) + Ok(value) } Err(e) => { self.optimizer.report(index, std::u64::MAX); diff --git a/core/src/rpc.rs b/core/src/rpc.rs index 52bee056ca..3f135cb3fe 100644 --- a/core/src/rpc.rs +++ b/core/src/rpc.rs @@ -12,7 +12,9 @@ use crate::{ use bincode::serialize; use jsonrpc_core::{Error, Metadata, Result}; use jsonrpc_derive::rpc; -use solana_client::rpc_request::{RpcEpochInfo, RpcVoteAccountInfo, RpcVoteAccountStatus}; +use solana_client::rpc_request::{ + Response, RpcEpochInfo, RpcResponseContext, RpcVoteAccountInfo, RpcVoteAccountStatus, +}; use solana_drone::drone::request_airdrop_transaction; use solana_ledger::{ bank_forks::BankForks, blocktree::Blocktree, rooted_slot_iterator::RootedSlotIterator, @@ -40,6 +42,13 @@ use std::{ time::{Duration, Instant}, }; +type RpcResponse = Result>; + +fn new_response(bank: &Bank, value: T) -> RpcResponse { + let context = RpcResponseContext { slot: bank.slot() }; + Ok(Response { context, value }) +} + #[derive(Debug, Clone)] pub struct JsonRpcConfig { pub enable_validator_exit: bool, // Enable the 'validatorExit' command @@ -100,12 +109,14 @@ impl JsonRpcRequestProcessor { pub fn get_account_info( &self, - pubkey: &Pubkey, + pubkey: Result, commitment: Option, - ) -> Result { - self.bank(commitment) - .get_account(&pubkey) - .ok_or_else(Error::invalid_request) + ) -> RpcResponse> { + let bank = &*self.bank(commitment); + match pubkey { + Ok(key) => new_response(bank, bank.get_account(&key)), + Err(e) => Err(e), + } } pub fn get_minimum_balance_for_rent_exemption( @@ -141,16 +152,43 @@ impl JsonRpcRequestProcessor { Ok(*self.bank(None).epoch_schedule()) } - pub fn get_balance(&self, pubkey: &Pubkey, commitment: Option) -> u64 { - self.bank(commitment).get_balance(&pubkey) + pub fn get_balance( + &self, + pubkey: Result, + commitment: Option, + ) -> RpcResponse { + let bank = &*self.bank(commitment); + match pubkey { + Ok(key) => new_response(bank, bank.get_balance(&key)), + Err(e) => Err(e), + } } fn get_recent_blockhash( &self, commitment: Option, - ) -> (String, FeeCalculator) { - let (blockhash, fee_calculator) = self.bank(commitment).confirmed_last_blockhash(); - (blockhash.to_string(), fee_calculator) + ) -> RpcResponse<(String, FeeCalculator)> { + let bank = &*self.bank(commitment); + let (blockhash, fee_calculator) = bank.confirmed_last_blockhash(); + new_response(bank, (blockhash.to_string(), fee_calculator)) + } + + pub fn confirm_transaction( + &self, + signature: Result, + commitment: Option, + ) -> RpcResponse { + let bank = &*self.bank(commitment); + match signature { + Err(e) => Err(e), + Ok(sig) => { + let status = bank.get_signature_confirmation_status(&sig); + match status { + Some((_, result)) => new_response(bank, result.is_ok()), + None => new_response(bank, false), + } + } + } } fn get_block_commitment(&self, block: Slot) -> (Option, u64) { @@ -333,7 +371,7 @@ pub trait RpcSol { meta: Self::Metadata, signature_str: String, commitment: Option, - ) -> Result; + ) -> RpcResponse; #[rpc(meta, name = "getAccountInfo")] fn get_account_info( @@ -341,7 +379,7 @@ pub trait RpcSol { meta: Self::Metadata, pubkey_str: String, commitment: Option, - ) -> Result; + ) -> RpcResponse>; #[rpc(meta, name = "getProgramAccounts")] fn get_program_accounts( @@ -375,7 +413,7 @@ pub trait RpcSol { meta: Self::Metadata, pubkey_str: String, commitment: Option, - ) -> Result; + ) -> RpcResponse; #[rpc(meta, name = "getClusterNodes")] fn get_cluster_nodes(&self, meta: Self::Metadata) -> Result>; @@ -409,7 +447,7 @@ pub trait RpcSol { &self, meta: Self::Metadata, commitment: Option, - ) -> Result<(String, FeeCalculator)>; + ) -> RpcResponse<(String, FeeCalculator)>; #[rpc(meta, name = "getSignatureStatus")] fn get_signature_status( @@ -521,20 +559,15 @@ impl RpcSol for RpcSolImpl { fn confirm_transaction( &self, meta: Self::Metadata, - signature_str: String, + id: String, commitment: Option, - ) -> Result { - debug!( - "confirm_transaction rpc request received: {:?}", - signature_str - ); - self.get_signature_status(meta, signature_str, commitment) - .map(|status_option| { - if status_option.is_none() { - return false; - } - status_option.unwrap().is_ok() - }) + ) -> RpcResponse { + debug!("confirm_transaction rpc request received: {:?}", id); + let signature = verify_signature(&id); + meta.request_processor + .read() + .unwrap() + .confirm_transaction(signature, commitment) } fn get_account_info( @@ -542,13 +575,13 @@ impl RpcSol for RpcSolImpl { meta: Self::Metadata, pubkey_str: String, commitment: Option, - ) -> Result { + ) -> RpcResponse> { debug!("get_account_info rpc request received: {:?}", pubkey_str); - let pubkey = verify_pubkey(pubkey_str)?; + let pubkey = verify_pubkey(pubkey_str); meta.request_processor .read() .unwrap() - .get_account_info(&pubkey, commitment) + .get_account_info(pubkey, commitment) } fn get_minimum_balance_for_rent_exemption( @@ -613,14 +646,13 @@ impl RpcSol for RpcSolImpl { meta: Self::Metadata, pubkey_str: String, commitment: Option, - ) -> Result { + ) -> RpcResponse { debug!("get_balance rpc request received: {:?}", pubkey_str); - let pubkey = verify_pubkey(pubkey_str)?; - Ok(meta - .request_processor + let pubkey = verify_pubkey(pubkey_str); + meta.request_processor .read() .unwrap() - .get_balance(&pubkey, commitment)) + .get_balance(pubkey, commitment) } fn get_cluster_nodes(&self, meta: Self::Metadata) -> Result> { @@ -707,13 +739,12 @@ impl RpcSol for RpcSolImpl { &self, meta: Self::Metadata, commitment: Option, - ) -> Result<(String, FeeCalculator)> { + ) -> RpcResponse<(String, FeeCalculator)> { debug!("get_recent_blockhash rpc request received"); - Ok(meta - .request_processor + meta.request_processor .read() .unwrap() - .get_recent_blockhash(commitment)) + .get_recent_blockhash(commitment) } fn get_signature_status( @@ -1150,10 +1181,15 @@ pub mod tests { bob_pubkey ); let res = io.handle_request_sync(&req, meta); - let expected = format!(r#"{{"jsonrpc":"2.0","result":20,"id":1}}"#); - let expected: Response = - serde_json::from_str(&expected).expect("expected response deserialization"); - let result: Response = serde_json::from_str(&res.expect("actual response")) + let expected = json!({ + "jsonrpc": "2.0", + "result": { + "context":{"slot":0}, + "value":20, + }, + "id": 1, + }); + let result = serde_json::from_str::(&res.expect("actual response")) .expect("actual response deserialization"); assert_eq!(expected, result); } @@ -1328,19 +1364,22 @@ pub mod tests { bob_pubkey ); let res = io.handle_request_sync(&req, meta); - let expected = r#"{ - "jsonrpc":"2.0", - "result":{ + let expected = json!({ + "jsonrpc": "2.0", + "result": { + "context":{"slot":0}, + "value":{ "owner": [0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0], "lamports": 20, "data": [], "executable": false, "rent_epoch": 0 }, - "id":1} - "#; + }, + "id": 1, + }); let expected: Response = - serde_json::from_str(&expected).expect("expected response deserialization"); + serde_json::from_value(expected).expect("expected response deserialization"); let result: Response = serde_json::from_str(&res.expect("actual response")) .expect("actual response deserialization"); assert_eq!(expected, result); @@ -1404,9 +1443,16 @@ pub mod tests { tx.signatures[0] ); let res = io.handle_request_sync(&req, meta); - let expected = format!(r#"{{"jsonrpc":"2.0","result":true,"id":1}}"#); + let expected = json!({ + "jsonrpc": "2.0", + "result": { + "context":{"slot":0}, + "value":true, + }, + "id": 1, + }); let expected: Response = - serde_json::from_str(&expected).expect("expected response deserialization"); + serde_json::from_value(expected).expect("expected response deserialization"); let result: Response = serde_json::from_str(&res.expect("actual response")) .expect("actual response deserialization"); assert_eq!(expected, result); @@ -1496,14 +1542,16 @@ pub mod tests { let res = io.handle_request_sync(&req, meta); let expected = json!({ "jsonrpc": "2.0", - "result": [ blockhash.to_string(), { + "result": { + "context":{"slot":0}, + "value":[ blockhash.to_string(), { "burnPercent": DEFAULT_BURN_PERCENT, "lamportsPerSignature": 0, "maxLamportsPerSignature": 0, "minLamportsPerSignature": 0, "targetLamportsPerSignature": 0, "targetSignaturesPerSlot": 0 - }], + }]}, "id": 1 }); let expected: Response = diff --git a/core/src/rpc_service.rs b/core/src/rpc_service.rs index 3f2456cca5..b7967efb45 100644 --- a/core/src/rpc_service.rs +++ b/core/src/rpc_service.rs @@ -229,7 +229,9 @@ mod tests { .request_processor .read() .unwrap() - .get_balance(&mint_keypair.pubkey(), None) + .get_balance(Ok(mint_keypair.pubkey()), None) + .unwrap() + .value ); rpc_service.exit(); rpc_service.join().unwrap(); diff --git a/core/tests/client.rs b/core/tests/client.rs index a3f81f36df..87f235c1f2 100644 --- a/core/tests/client.rs +++ b/core/tests/client.rs @@ -1,5 +1,6 @@ use solana_client::rpc_client::RpcClient; use solana_core::validator::new_validator_for_tests; +use solana_sdk::commitment_config::CommitmentConfig; use solana_sdk::pubkey::Pubkey; use solana_sdk::signature::KeypairUtil; use solana_sdk::system_transaction; @@ -22,7 +23,6 @@ fn test_rpc_client() { ); assert_eq!(client.get_balance(&bob_pubkey).unwrap(), 0); - assert_eq!(client.get_balance(&alice.pubkey()).unwrap(), 10000); let (blockhash, _fee_calculator) = client.get_recent_blockhash().unwrap(); @@ -34,14 +34,13 @@ fn test_rpc_client() { let now = Instant::now(); while now.elapsed().as_secs() <= 20 { - let response = client.confirm_transaction(signature.as_str()); + let response = client + .confirm_transaction_with_commitment(signature.as_str(), CommitmentConfig::default()) + .unwrap(); - match response { - Ok(true) => { - confirmed_tx = true; - break; - } - _ => (), + if response.value { + confirmed_tx = true; + break; } sleep(Duration::from_millis(500)); diff --git a/core/tests/rpc.rs b/core/tests/rpc.rs index 1fb9970baa..78470cb965 100644 --- a/core/tests/rpc.rs +++ b/core/tests/rpc.rs @@ -34,7 +34,11 @@ fn test_rpc_send_tx() { .send() .unwrap(); let json: Value = serde_json::from_str(&response.text().unwrap()).unwrap(); - let blockhash: Hash = json["result"][0].as_str().unwrap().parse().unwrap(); + let blockhash: Hash = json["result"]["value"][0] + .as_str() + .unwrap() + .parse() + .unwrap(); info!("blockhash: {:?}", blockhash); let tx = system_transaction::transfer(&alice, &bob_pubkey, 20, blockhash); @@ -78,7 +82,7 @@ fn test_rpc_send_tx() { let response_json_text = response.text().unwrap(); let json: Value = serde_json::from_str(&response_json_text).unwrap(); - if true == json["result"] { + if true == json["result"]["value"] { confirmed_tx = true; break; }