Allow for customisation of chain selection systems (#2240)

* move SelectChain trait out of client

* Extend SelectChain, move longest chain implementation into it

* Bring SelectChain into service

* implement LongestChain SelectChain

* implement longest chain for node

* update Cargo.lock's

* in between erroring tests

* deprecate ::backend and ::import_lock

* Remove unneded space

Co-Authored-By: gnunicorn <ben.kampmann@googlemail.com>

* Remove unneded space

Co-Authored-By: gnunicorn <ben.kampmann@googlemail.com>

* Fixes test compilation

* remove todo

* re-enable client test

* add doc

* fixing tests

* Clarify SelectChain Interface, intended implementation and usage

* minor components cleanups

* minor cleanups

* Update lock files

* Implement cleaner interface for SelectChain

* addressing comments

* Updating tests

* bump node runtime impl version

* address grumbles
This commit is contained in:
Benjamin Kampmann
2019-05-10 14:08:12 +02:00
committed by Gavin Wood
parent 32fdeed21c
commit 18ca0170c3
22 changed files with 717 additions and 339 deletions
@@ -105,5 +105,11 @@ error_chain! {
description("Import failed"),
display("Import failed: {}", reason),
}
/// Error from the client while importing
ChainLookup(reason: String) {
description("Looking up chain failed"),
display("Chain lookup failed: {}", reason),
}
}
}
@@ -40,6 +40,7 @@ pub use inherents::InherentData;
pub mod offline_tracker;
pub mod error;
mod block_import;
mod select_chain;
pub mod import_queue;
pub mod evaluation;
@@ -50,6 +51,7 @@ pub use self::error::{Error, ErrorKind};
pub use block_import::{
BlockImport, BlockOrigin, ForkChoiceStrategy, ImportedAux, ImportBlock, ImportResult, JustificationImport,
};
pub use select_chain::SelectChain;
/// Trait for getting the authorities at a given block.
pub trait Authorities<B: Block> {
@@ -0,0 +1,54 @@
// Copyright 2019 Parity Technologies (UK) Ltd.
// This file is part of Substrate Consensus Common.
// Substrate Demo is free software: you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation, either version 3 of the License, or
// (at your option) any later version.
// Substrate Consensus Common is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
// You should have received a copy of the GNU General Public License
// along with Substrate Consensus Common. If not, see <http://www.gnu.org/licenses/>.
use crate::error::Error;
use runtime_primitives::traits::{Block as BlockT, NumberFor};
/// The SelectChain trait defines the strategy upon which the head is chosen
/// if multiple forks are present for an opaque definition of "best" in the
/// specific chain build.
///
/// The Strategy can be customised for the two use cases of authoring new blocks
/// upon the best chain or which fork to finalise. Unless implemented differently
/// by default finalisation methods fall back to use authoring, so as a minimum
/// `_authoring`-functions must be implemented.
///
/// Any particular user must make explicit, however, whether they intend to finalise
/// or author through the using the right function call, as these might differ in
/// some implementations.
///
/// Non-deterministicly finalising chains may only use the `_authoring` functions.
pub trait SelectChain<Block: BlockT>: Sync + Send + Clone {
/// Get all leaves of the chain: block hashes that have no children currently.
/// Leaves that can never be finalized will not be returned.
fn leaves(&self) -> Result<Vec<<Block as BlockT>::Hash>, Error>;
/// Among those `leaves` deterministically pick one chain as the generally
/// best chain to author new blocks upon and probably finalize.
fn best_chain(&self) -> Result<<Block as BlockT>::Header, Error>;
/// Get the best ancestor of `target_hash` that we should attempt
/// to finalize next.
fn finality_target(
&self,
target_hash: <Block as BlockT>::Hash,
_maybe_max_number: Option<NumberFor<Block>>
) -> Result<Option<<Block as BlockT>::Hash>, Error> {
Ok(Some(target_hash))
}
}