diff --git a/substrate/rpc/src/state/mod.rs b/substrate/rpc/src/state/mod.rs index c0724f9de3f63..25f985c206cdc 100644 --- a/substrate/rpc/src/state/mod.rs +++ b/substrate/rpc/src/state/mod.rs @@ -43,37 +43,21 @@ build_rpc_trait! { pub trait StateApi { type Metadata; - /// Returns a storage entry at a specific block's state. - #[rpc(name = "state_getStorageAt")] - fn storage_at(&self, StorageKey, Hash) -> Result>; - /// Call a contract at a block's state. - #[rpc(name = "state_callAt")] - fn call_at(&self, String, Vec, Hash) -> Result>; + #[rpc(name = "state_call", alias = ["state_callAt", ])] + fn call(&self, String, Vec, Trailing) -> Result>; + + /// Returns a storage entry at a specific block's state. + #[rpc(name = "state_getStorage", alias = ["state_getStorageAt", ])] + fn storage(&self, StorageKey, Trailing) -> Result>; /// Returns the hash of a storage entry at a block's state. - #[rpc(name = "state_getStorageHashAt")] - fn storage_hash_at(&self, StorageKey, Hash) -> Result>; + #[rpc(name = "state_getStorageHash", alias = ["state_getStorageHashAt", ])] + fn storage_hash(&self, StorageKey, Trailing) -> Result>; /// Returns the size of a storage entry at a block's state. - #[rpc(name = "state_getStorageSizeAt")] - fn storage_size_at(&self, StorageKey, Hash) -> Result>; - - /// Returns the hash of a storage entry at the best block. - #[rpc(name = "state_getStorageHash")] - fn storage_hash(&self, StorageKey) -> Result>; - - /// Returns the size of a storage entry at the best block. - #[rpc(name = "state_getStorageSize")] - fn storage_size(&self, StorageKey) -> Result>; - - /// Returns a storage entry at the best block. - #[rpc(name = "state_getStorage")] - fn storage(&self, StorageKey) -> Result>; - - /// Call a contract at the best block. - #[rpc(name = "state_call")] - fn call(&self, String, Vec) -> Result>; + #[rpc(name = "state_getStorageSize", alias = ["state_getStorageSizeAt", ])] + fn storage_size(&self, StorageKey, Trailing) -> Result>; #[pubsub(name = "state_storage")] { /// New storage subscription @@ -105,6 +89,19 @@ impl State { } } +impl State where + Block: BlockT + 'static, + B: client::backend::Backend + Send + Sync + 'static, + E: CallExecutor + Send + Sync + 'static, +{ + fn unwrap_or_best(&self, hash: Trailing) -> Result { + Ok(match hash.into() { + None => self.client.info()?.chain.best_hash, + Some(hash) => hash, + }) + } +} + impl StateApi for State where Block: BlockT + 'static, B: client::backend::Backend + Send + Sync + 'static, @@ -112,40 +109,25 @@ impl StateApi for State where { type Metadata = ::metadata::Metadata; - fn storage_at(&self, key: StorageKey, block: Block::Hash) -> Result> { - trace!(target: "rpc", "Querying storage at {:?} for key {}", block, HexDisplay::from(&key.0)); - Ok(self.client.storage(&BlockId::Hash(block), &key)?) - } - - fn call_at(&self, method: String, data: Vec, block: Block::Hash) -> Result> { + fn call(&self, method: String, data: Vec, block: Trailing) -> Result> { + let block = self.unwrap_or_best(block)?; trace!(target: "rpc", "Calling runtime at {:?} for method {} ({})", block, method, HexDisplay::from(&data)); Ok(self.client.executor().call(&BlockId::Hash(block), &method, &data)?.return_data) } - fn storage_hash_at(&self, key: StorageKey, block: Block::Hash) -> Result> { - use runtime_primitives::traits::{Hash, Header as HeaderT}; - Ok(self.storage_at(key, block)?.map(|x| ::Hashing::hash(&x.0))) - } - - fn storage_size_at(&self, key: StorageKey, block: Block::Hash) -> Result> { - Ok(self.storage_at(key, block)?.map(|x| x.0.len() as u64)) - } - - fn storage_hash(&self, key: StorageKey) -> Result> { - self.storage_hash_at(key, self.client.info()?.chain.best_hash) - } - - fn storage_size(&self, key: StorageKey) -> Result> { - self.storage_size_at(key, self.client.info()?.chain.best_hash) + fn storage(&self, key: StorageKey, block: Trailing) -> Result> { + let block = self.unwrap_or_best(block)?; + trace!(target: "rpc", "Querying storage at {:?} for key {}", block, HexDisplay::from(&key.0)); + Ok(self.client.storage(&BlockId::Hash(block), &key)?) } - fn storage(&self, key: StorageKey) -> Result> { - self.storage_at(key, self.client.info()?.chain.best_hash) - + fn storage_hash(&self, key: StorageKey, block: Trailing) -> Result> { + use runtime_primitives::traits::{Hash, Header as HeaderT}; + Ok(self.storage(key, block)?.map(|x| ::Hashing::hash(&x.0))) } - fn call(&self, method: String, data: Vec) -> Result> { - self.call_at(method, data, self.client.info()?.chain.best_hash) + fn storage_size(&self, key: StorageKey, block: Trailing) -> Result> { + Ok(self.storage(key, block)?.map(|x| x.0.len() as u64)) } fn subscribe_storage( @@ -166,14 +148,14 @@ impl StateApi for State where // initial values let initial = stream::iter_result(keys .map(|keys| { + let block = self.client.info().map(|info| info.chain.best_hash).unwrap_or_default(); let changes = keys .into_iter() - .map(|key| self.storage(key.clone()) + .map(|key| self.storage(key.clone(), Some(block.clone()).into()) .map(|val| (key.clone(), val)) .unwrap_or_else(|_| (key, None)) ) .collect(); - let block = self.client.info().map(|info| info.chain.best_hash).unwrap_or_default(); vec![Ok(Ok(StorageChangeSet { block, changes }))] }).unwrap_or_default()); diff --git a/substrate/rpc/src/state/tests.rs b/substrate/rpc/src/state/tests.rs index 0fc33818684e9..1ab9d1896a1d9 100644 --- a/substrate/rpc/src/state/tests.rs +++ b/substrate/rpc/src/state/tests.rs @@ -31,7 +31,7 @@ fn should_return_storage() { let client = State::new(client, core.executor()); assert_matches!( - client.storage_at(StorageKey(vec![10]), genesis_hash), + client.storage(StorageKey(vec![10]), Some(genesis_hash).into()), Ok(None) ) } @@ -44,7 +44,7 @@ fn should_call_contract() { let client = State::new(client, core.executor()); assert_matches!( - client.call_at("balanceOf".into(), vec![1,2,3], genesis_hash), + client.call("balanceOf".into(), vec![1,2,3], Some(genesis_hash).into()), Err(Error(ErrorKind::Client(client::error::ErrorKind::Execution(_)), _)) ) }