Fixes GrandpaApi implementation and usage

This commit is contained in:
Bastian Köcher
2018-11-15 17:34:55 +01:00
parent 1cb0bbc48b
commit 3cd2739f66
10 changed files with 67 additions and 71 deletions
+2
View File
@@ -1804,6 +1804,7 @@ dependencies = [
"srml-treasury 0.1.0", "srml-treasury 0.1.0",
"srml-upgrade-key 0.1.0", "srml-upgrade-key 0.1.0",
"substrate-client 0.1.0", "substrate-client 0.1.0",
"substrate-fg-primitives 0.1.0",
"substrate-keyring 0.1.0", "substrate-keyring 0.1.0",
"substrate-primitives 0.1.0", "substrate-primitives 0.1.0",
] ]
@@ -3186,6 +3187,7 @@ dependencies = [
"parity-codec 2.1.5 (registry+https://github.com/rust-lang/crates.io-index)", "parity-codec 2.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
"parity-codec-derive 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)", "parity-codec-derive 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"sr-primitives 0.1.0", "sr-primitives 0.1.0",
"sr-std 0.1.0",
"substrate-client 0.1.0", "substrate-client 0.1.0",
"substrate-primitives 0.1.0", "substrate-primitives 0.1.0",
] ]
@@ -9,6 +9,7 @@ substrate-primitives = { path = "../../primitives", default-features = false }
parity-codec = { version = "2.1", default-features = false } parity-codec = { version = "2.1", default-features = false }
parity-codec-derive = { version = "2.1", default-features = false } parity-codec-derive = { version = "2.1", default-features = false }
sr-primitives = { path = "../../sr-primitives", default-features = false } sr-primitives = { path = "../../sr-primitives", default-features = false }
sr-std = { path = "../../sr-std", default-features = false }
[features] [features]
default = ["std"] default = ["std"]
@@ -18,4 +19,5 @@ std = [
"parity-codec/std", "parity-codec/std",
"parity-codec-derive/std", "parity-codec-derive/std",
"sr-primitives/std", "sr-primitives/std",
"sr-std/std",
] ]
@@ -28,8 +28,11 @@ extern crate parity_codec_derive;
#[macro_use] #[macro_use]
extern crate substrate_client as client; extern crate substrate_client as client;
extern crate sr_std as rstd;
use substrate_primitives::AuthorityId; use substrate_primitives::AuthorityId;
use sr_primitives::traits::{Block as BlockT, DigestFor, NumberFor}; use sr_primitives::traits::{Block as BlockT, DigestFor, NumberFor};
use rstd::vec::Vec;
/// A scheduled change of authority set. /// A scheduled change of authority set.
#[cfg_attr(feature = "std", derive(Debug, PartialEq))] #[cfg_attr(feature = "std", derive(Debug, PartialEq))]
@@ -81,55 +84,3 @@ decl_runtime_apis! {
fn grandpa_authorities() -> Vec<(AuthorityId, u64)>; fn grandpa_authorities() -> Vec<(AuthorityId, u64)>;
} }
} }
#[cfg(feature = "std")]
mod implementation {
use super::{GrandpaApi, ScheduledChange};
use sr_primitives::traits::{Block as BlockT, DigestFor, NumberFor};
use sr_primitives::generic::BlockId;
use parity_codec::{Encode, Decode};
use client::{Client, error::Error as ClientError, backend::Backend, CallExecutor};
use client::runtime_api::{CallApiAt, Core as CoreAPI};
use substrate_primitives::{AuthorityId, H256, Blake2Hasher};
// TODO [basti]: do this implementation in runtime.
impl<B, E, Block: BlockT<Hash=H256>, RA> GrandpaApi<Block> for Client<B, E, Block, RA> where
B: Backend<Block, Blake2Hasher> + 'static,
E: CallExecutor<Block, Blake2Hasher> + 'static + Clone + Send + Sync,
DigestFor<Block>: Encode,
RA: CoreAPI<Block>,
{
fn grandpa_authorities(&self, at: &BlockId<Block>) -> Result<Vec<(AuthorityId, u64)>, ClientError> {
let raw = self.call_api_at(
&at,
::AUTHORITIES_CALL,
Encode::encode(&()),
&mut Default::default(),
&mut None,
);
// TODO [basti]: implement this in runtime with macro.
match Decode::decode(&mut &raw[..]) {
Some(x) => Ok(x),
None => Err(::client::error::ErrorKind::CallResultDecode(::AUTHORITIES_CALL).into()),
}
}
fn grandpa_pending_change(&self, at: &BlockId<Block>, digest: DigestFor<Block>)
-> Result<Option<ScheduledChange<NumberFor<Block>>>, ClientError>
{
let raw = self.call_api_at(
at,
::PENDING_CHANGE_CALL,
digest.encode(),
&mut Default::default(),
&mut None,
);
match Decode::decode(&mut &raw[..]) {
Some(x) => Ok(x),
None => Err(::client::error::ErrorKind::CallResultDecode(::PENDING_CHANGE_CALL).into()),
}
}
}
}
+13 -16
View File
@@ -84,11 +84,11 @@ use futures::stream::Fuse;
use futures::sync::mpsc; use futures::sync::mpsc;
use client::{Client, error::Error as ClientError, ImportNotifications, backend::Backend, CallExecutor}; use client::{Client, error::Error as ClientError, ImportNotifications, backend::Backend, CallExecutor};
use client::blockchain::HeaderBackend; use client::blockchain::HeaderBackend;
use client::runtime_api::{CallApiAt, TaggedTransactionQueue, Core as CoreAPI}; use client::runtime_api::TaggedTransactionQueue;
use codec::{Encode, Decode}; use codec::{Encode, Decode};
use consensus_common::{BlockImport, ImportBlock, ImportResult}; use consensus_common::{BlockImport, ImportBlock, ImportResult};
use runtime_primitives::traits::{ use runtime_primitives::traits::{
NumberFor, Block as BlockT, Header as HeaderT, DigestFor, NumberFor, Block as BlockT, Header as HeaderT, DigestFor, ProvideRuntimeApi
}; };
use fg_primitives::GrandpaApi; use fg_primitives::GrandpaApi;
use runtime_primitives::generic::BlockId; use runtime_primitives::generic::BlockId;
@@ -773,18 +773,16 @@ impl<B, E, Block: BlockT<Hash=H256>, N, RA> voter::Environment<Block::Hash, Numb
/// This scans each imported block for signals of changing authority set. /// This scans each imported block for signals of changing authority set.
/// When using GRANDPA, the block import worker should be using this block import /// When using GRANDPA, the block import worker should be using this block import
/// object. /// object.
pub struct GrandpaBlockImport<B, E, Block: BlockT<Hash=H256>, Api, RA> { pub struct GrandpaBlockImport<B, E, Block: BlockT<Hash=H256>, RA> {
inner: Arc<Client<B, E, Block, RA>>, inner: Arc<Client<B, E, Block, RA>>,
authority_set: SharedAuthoritySet<Block::Hash, NumberFor<Block>>, authority_set: SharedAuthoritySet<Block::Hash, NumberFor<Block>>,
api_client: Api,
} }
impl<B, E, Block: BlockT<Hash=H256>, Api, RA> BlockImport<Block> for GrandpaBlockImport<B, E, Block, Api, RA> where impl<B, E, Block: BlockT<Hash=H256>, RA> BlockImport<Block> for GrandpaBlockImport<B, E, Block, RA> where
B: Backend<Block, Blake2Hasher> + 'static, B: Backend<Block, Blake2Hasher> + 'static,
E: CallExecutor<Block, Blake2Hasher> + 'static + Clone + Send + Sync, E: CallExecutor<Block, Blake2Hasher> + 'static + Clone + Send + Sync,
DigestFor<Block>: Encode, DigestFor<Block>: Encode,
Api: GrandpaApi<Block>, RA: GrandpaApi<Block> + TaggedTransactionQueue<Block>,
RA: TaggedTransactionQueue<Block> + Send + Sync, // necessary for client to import `BlockImport`.
{ {
type Error = ClientError; type Error = ClientError;
@@ -793,7 +791,7 @@ impl<B, E, Block: BlockT<Hash=H256>, Api, RA> BlockImport<Block> for GrandpaBloc
{ {
use authorities::PendingChange; use authorities::PendingChange;
let maybe_change = self.api_client.grandpa_pending_change( let maybe_change = self.inner.runtime_api().grandpa_pending_change(
&BlockId::hash(*block.header.parent_hash()), &BlockId::hash(*block.header.parent_hash()),
&block.header.digest().clone(), &block.header.digest().clone(),
)?; )?;
@@ -839,13 +837,12 @@ pub struct LinkHalf<B, E, Block: BlockT<Hash=H256>, RA> {
/// Make block importer and link half necessary to tie the background voter /// Make block importer and link half necessary to tie the background voter
/// to it. /// to it.
pub fn block_import<B, E, Block: BlockT<Hash=H256>, Api, RA>(client: Arc<Client<B, E, Block, RA>>, api_client: Api) pub fn block_import<B, E, Block: BlockT<Hash=H256>, RA>(client: Arc<Client<B, E, Block, RA>>)
-> Result<(GrandpaBlockImport<B, E, Block, Api, RA>, LinkHalf<B, E, Block, RA>), ClientError> -> Result<(GrandpaBlockImport<B, E, Block, RA>, LinkHalf<B, E, Block, RA>), ClientError>
where where
B: Backend<Block, Blake2Hasher> + 'static, B: Backend<Block, Blake2Hasher> + 'static,
E: CallExecutor<Block, Blake2Hasher> + 'static, E: CallExecutor<Block, Blake2Hasher> + 'static + Clone + Send + Sync,
Api: GrandpaApi<Block>, RA: GrandpaApi<Block>,
RA: Send + Sync,
{ {
use runtime_primitives::traits::Zero; use runtime_primitives::traits::Zero;
let authority_set = match client.backend().get_aux(AUTHORITY_SET_KEY)? { let authority_set = match client.backend().get_aux(AUTHORITY_SET_KEY)? {
@@ -856,7 +853,7 @@ pub fn block_import<B, E, Block: BlockT<Hash=H256>, Api, RA>(client: Arc<Client<
// no authority set on disk: fetch authorities from genesis state. // no authority set on disk: fetch authorities from genesis state.
// if genesis state is not available, we may be a light client, but these // if genesis state is not available, we may be a light client, but these
// are unsupported for following GRANDPA directly. // are unsupported for following GRANDPA directly.
let genesis_authorities = api_client let genesis_authorities = client.runtime_api()
.grandpa_authorities(&BlockId::number(Zero::zero()))?; .grandpa_authorities(&BlockId::number(Zero::zero()))?;
let authority_set = SharedAuthoritySet::genesis(genesis_authorities); let authority_set = SharedAuthoritySet::genesis(genesis_authorities);
@@ -873,7 +870,7 @@ pub fn block_import<B, E, Block: BlockT<Hash=H256>, Api, RA>(client: Arc<Client<
}; };
Ok(( Ok((
GrandpaBlockImport { inner: client.clone(), authority_set: authority_set.clone(), api_client }, GrandpaBlockImport { inner: client.clone(), authority_set: authority_set.clone() },
LinkHalf { client, authority_set }, LinkHalf { client, authority_set },
)) ))
} }
+4 -2
View File
@@ -14,7 +14,8 @@ parity-codec-derive = "2.1"
sr-std = { path = "../../core/sr-std" } sr-std = { path = "../../core/sr-std" }
srml-support = { path = "../../srml/support" } srml-support = { path = "../../srml/support" }
substrate-primitives = { path = "../../core/primitives" } substrate-primitives = { path = "../../core/primitives" }
substrate-client = { path = "../../core/client", optional = true } substrate-fg-primitives = { path = "../../core/finality-grandpa/primitives" }
substrate-client = { path = "../../core/client" }
substrate-keyring = { path = "../../core/keyring" } substrate-keyring = { path = "../../core/keyring" }
srml-balances = { path = "../../srml/balances" } srml-balances = { path = "../../srml/balances" }
srml-consensus = { path = "../../srml/consensus" } srml-consensus = { path = "../../srml/consensus" }
@@ -57,5 +58,6 @@ std = [
"serde_derive", "serde_derive",
"serde/std", "serde/std",
"safe-mix/std", "safe-mix/std",
"substrate-client", "substrate-client/std",
"substrate-fg-primitives/std",
] ]
+28 -1
View File
@@ -56,6 +56,7 @@ extern crate srml_upgrade_key as upgrade_key;
#[macro_use] #[macro_use]
extern crate sr_version as version; extern crate sr_version as version;
extern crate node_primitives; extern crate node_primitives;
extern crate substrate_fg_primitives;
#[cfg(feature = "std")] #[cfg(feature = "std")]
use codec::{Encode, Decode}; use codec::{Encode, Decode};
@@ -72,7 +73,7 @@ use client::runtime_api::ApiExt;
use runtime_primitives::ApplyResult; use runtime_primitives::ApplyResult;
use runtime_primitives::transaction_validity::TransactionValidity; use runtime_primitives::transaction_validity::TransactionValidity;
use runtime_primitives::generic; use runtime_primitives::generic;
use runtime_primitives::traits::{Convert, BlakeTwo256, Block as BlockT}; use runtime_primitives::traits::{Convert, BlakeTwo256, Block as BlockT, DigestFor, NumberFor};
#[cfg(feature = "std")] #[cfg(feature = "std")]
use runtime_primitives::traits::ApiRef; use runtime_primitives::traits::ApiRef;
#[cfg(feature = "std")] #[cfg(feature = "std")]
@@ -84,6 +85,7 @@ use council::seats as council_seats;
#[cfg(any(feature = "std", test))] #[cfg(any(feature = "std", test))]
use version::NativeVersion; use version::NativeVersion;
use substrate_primitives::OpaqueMetadata; use substrate_primitives::OpaqueMetadata;
use substrate_fg_primitives::{runtime::GrandpaApi, ScheduledChange};
#[cfg(any(feature = "std", test))] #[cfg(any(feature = "std", test))]
pub use runtime_primitives::BuildStorage; pub use runtime_primitives::BuildStorage;
@@ -395,6 +397,19 @@ impl client::runtime_api::Metadata<GBlock> for ClientWithApi {
} }
} }
#[cfg(feature = "std")]
impl substrate_fg_primitives::GrandpaApi<GBlock> for ClientWithApi {
fn grandpa_pending_change(&self, at: &GBlockId, digest: &DigestFor<GBlock>)
-> Result<Option<ScheduledChange<NumberFor<GBlock>>>, client::error::Error> {
self.call_api_at(at, "grandpa_pending_change", digest)
}
fn grandpa_authorities(&self, at: &GBlockId)
-> Result<Vec<(AuthorityId, u64)>, client::error::Error> {
self.call_api_at(at, "grandpa_authorities", &())
}
}
impl_runtime_apis! { impl_runtime_apis! {
impl Core<Block> for Runtime { impl Core<Block> for Runtime {
fn version() -> RuntimeVersion { fn version() -> RuntimeVersion {
@@ -447,4 +462,16 @@ impl_runtime_apis! {
Executive::validate_transaction(tx) Executive::validate_transaction(tx)
} }
} }
impl GrandpaApi<Block> for ClientWithApi {
fn grandpa_pending_change(digest: DigestFor<Block>)
-> Option<ScheduledChange<NumberFor<Block>>> {
unimplemented!("Robert, where is the impl?")
}
fn grandpa_authorities() -> Vec<(SessionKey, u64)> {
unimplemented!("Robert, where is the impl?")
}
}
} }
+13
View File
@@ -526,6 +526,7 @@ dependencies = [
"srml-treasury 0.1.0", "srml-treasury 0.1.0",
"srml-upgrade-key 0.1.0", "srml-upgrade-key 0.1.0",
"substrate-client 0.1.0", "substrate-client 0.1.0",
"substrate-fg-primitives 0.1.0",
"substrate-primitives 0.1.0", "substrate-primitives 0.1.0",
] ]
@@ -1272,6 +1273,18 @@ dependencies = [
"wasmi 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)", "wasmi 0.4.1 (registry+https://github.com/rust-lang/crates.io-index)",
] ]
[[package]]
name = "substrate-fg-primitives"
version = "0.1.0"
dependencies = [
"parity-codec 2.1.5 (registry+https://github.com/rust-lang/crates.io-index)",
"parity-codec-derive 2.1.0 (registry+https://github.com/rust-lang/crates.io-index)",
"sr-primitives 0.1.0",
"sr-std 0.1.0",
"substrate-client 0.1.0",
"substrate-primitives 0.1.0",
]
[[package]] [[package]]
name = "substrate-keyring" name = "substrate-keyring"
version = "0.1.0" version = "0.1.0"
+2
View File
@@ -12,6 +12,7 @@ safe-mix = { version = "1.0", default-features = false }
parity-codec-derive = { version = "2.1" } parity-codec-derive = { version = "2.1" }
parity-codec = { version = "2.1", default-features = false } parity-codec = { version = "2.1", default-features = false }
substrate-primitives = { path = "../../../core/primitives", default-features = false } substrate-primitives = { path = "../../../core/primitives", default-features = false }
substrate-fg-primitives = { path = "../../../core/finality-grandpa/primitives", default-features = false }
substrate-client = { path = "../../../core/client", default-features = false } substrate-client = { path = "../../../core/client", default-features = false }
sr-std = { path = "../../../core/sr-std", default-features = false } sr-std = { path = "../../../core/sr-std", default-features = false }
srml-support = { path = "../../../srml/support", default-features = false } srml-support = { path = "../../../srml/support", default-features = false }
@@ -38,6 +39,7 @@ std = [
"parity-codec/std", "parity-codec/std",
"substrate-primitives/std", "substrate-primitives/std",
"substrate-client/std", "substrate-client/std",
"substrate-fg-primitives/std",
"sr-std/std", "sr-std/std",
"srml-support/std", "srml-support/std",
"srml-balances/std", "srml-balances/std",