123use std::sync::Arc;4use std::time::Duration;5use sc_client_api::ExecutorProvider;6use sc_consensus::LongestChain;7use nft_runtime::{self, opaque::Block, RuntimeApi};8use sc_service::{error::{Error as ServiceError}, AbstractService, Configuration, ServiceBuilder};9use sp_inherents::InherentDataProviders;10use sc_executor::native_executor_instance;11pub use sc_executor::NativeExecutor;12use sp_consensus_aura::sr25519::{AuthorityPair as AuraPair};13use sc_finality_grandpa::{14 FinalityProofProvider as GrandpaFinalityProofProvider, StorageAndProofProvider, SharedVoterState,15};161718native_executor_instance!(19 pub Executor,20 nft_runtime::api::dispatch,21 nft_runtime::native_version,22);232425262728macro_rules! new_full_start {29 ($config:expr) => {{30 use jsonrpc_core::IoHandler;31 use std::sync::Arc;32 use sp_consensus_aura::sr25519::AuthorityPair as AuraPair;3334 let mut import_setup = None;35 let inherent_data_providers = sp_inherents::InherentDataProviders::new();3637 let builder = sc_service::ServiceBuilder::new_full::<38 nft_runtime::opaque::Block,39 nft_runtime::RuntimeApi,40 crate::service::Executor41 >($config)?42 .with_select_chain(|_config, backend| {43 Ok(sc_consensus::LongestChain::new(backend.clone()))44 })?45 .with_transaction_pool(|builder| {46 let pool_api = sc_transaction_pool::FullChainApi::new(47 builder.client().clone(),48 );49 Ok(sc_transaction_pool::BasicPool::new(50 builder.config().transaction_pool.clone(),51 std::sync::Arc::new(pool_api),52 builder.prometheus_registry(),53 ))54 })?55 .with_import_queue(|56 _config,57 client,58 mut select_chain,59 _transaction_pool,60 spawn_task_handle,61 registry,62 | {63 let select_chain = select_chain.take()64 .ok_or_else(|| sc_service::Error::SelectChainRequired)?;6566 let (grandpa_block_import, grandpa_link) = sc_finality_grandpa::block_import(67 client.clone(),68 &(client.clone() as Arc<_>),69 select_chain,70 )?;7172 let aura_block_import = sc_consensus_aura::AuraBlockImport::<_, _, _, AuraPair>::new(73 grandpa_block_import.clone(), client.clone(),74 );7576 let import_queue = sc_consensus_aura::import_queue::<_, _, _, AuraPair, _>(77 sc_consensus_aura::slot_duration(&*client)?,78 aura_block_import,79 Some(Box::new(grandpa_block_import.clone())),80 None,81 client,82 inherent_data_providers.clone(),83 spawn_task_handle,84 registry,85 )?;8687 import_setup = Some((grandpa_block_import, grandpa_link));8889 Ok(import_queue)90 })?91 .with_rpc_extensions(|builder| -> Result<IoHandler<sc_rpc::Metadata>, _> {92 let handler = pallet_contracts_rpc::Contracts::new(builder.client().clone());93 let delegate = pallet_contracts_rpc::ContractsApi::to_delegate(handler);9495 let mut io = IoHandler::default();96 io.extend_with(delegate);97 Ok(io)98 })?;99100 (builder, import_setup, inherent_data_providers)101 }}102}103104105pub fn new_full(config: Configuration) -> Result<impl AbstractService, ServiceError> {106 let role = config.role.clone();107 let force_authoring = config.force_authoring;108 let name = config.network.node_name.clone();109 let disable_grandpa = config.disable_grandpa;110111 let (builder, mut import_setup, inherent_data_providers) = new_full_start!(config);112113 let (block_import, grandpa_link) =114 import_setup.take()115 .expect("Link Half and Block Import are present for Full Services or setup failed before. qed");116117 let service = builder118 .with_finality_proof_provider(|client, backend| {119 120 let provider = client as Arc<dyn StorageAndProofProvider<_, _>>;121 Ok(Arc::new(GrandpaFinalityProofProvider::new(backend, provider)) as _)122 })?123 .build_full()?;124125 if role.is_authority() {126 let proposer = sc_basic_authorship::ProposerFactory::new(127 service.client(),128 service.transaction_pool(),129 service.prometheus_registry().as_ref(),130 );131132 let client = service.client();133 let select_chain = service.select_chain()134 .ok_or(ServiceError::SelectChainRequired)?;135136 let can_author_with =137 sp_consensus::CanAuthorWithNativeVersion::new(client.executor().clone());138139 let aura = sc_consensus_aura::start_aura::<_, _, _, _, _, AuraPair, _, _, _>(140 sc_consensus_aura::slot_duration(&*client)?,141 client,142 select_chain,143 block_import,144 proposer,145 service.network(),146 inherent_data_providers.clone(),147 force_authoring,148 service.keystore(),149 can_author_with,150 )?;151152 153 154 service.spawn_essential_task_handle().spawn_blocking("aura", aura);155 }156157 158 159 let keystore = if role.is_authority() {160 Some(service.keystore() as sp_core::traits::BareCryptoStorePtr)161 } else {162 None163 };164165 let grandpa_config = sc_finality_grandpa::Config {166 167 gossip_duration: Duration::from_millis(333),168 justification_period: 512,169 name: Some(name),170 observer_enabled: false,171 keystore,172 is_authority: role.is_network_authority(),173 };174175 let enable_grandpa = !disable_grandpa;176 if enable_grandpa {177 178 179 180 181 182 183 let grandpa_config = sc_finality_grandpa::GrandpaParams {184 config: grandpa_config,185 link: grandpa_link,186 network: service.network(),187 inherent_data_providers: inherent_data_providers.clone(),188 telemetry_on_connect: Some(service.telemetry_on_connect_stream()),189 voting_rule: sc_finality_grandpa::VotingRulesBuilder::default().build(),190 prometheus_registry: service.prometheus_registry(),191 shared_voter_state: SharedVoterState::empty(),192 };193194 195 196 service.spawn_essential_task_handle().spawn_blocking(197 "grandpa-voter",198 sc_finality_grandpa::run_grandpa_voter(grandpa_config)?199 );200 } else {201 sc_finality_grandpa::setup_disabled_grandpa(202 service.client(),203 &inherent_data_providers,204 service.network(),205 )?;206 }207208 Ok(service)209}210211212pub fn new_light(config: Configuration) -> Result<impl AbstractService, ServiceError> {213 let inherent_data_providers = InherentDataProviders::new();214215 ServiceBuilder::new_light::<Block, RuntimeApi, Executor>(config)?216 .with_select_chain(|_config, backend| {217 Ok(LongestChain::new(backend.clone()))218 })?219 .with_transaction_pool(|builder| {220 let fetcher = builder.fetcher()221 .ok_or_else(|| "Trying to start light transaction pool without active fetcher")?;222223 let pool_api = sc_transaction_pool::LightChainApi::new(224 builder.client().clone(),225 fetcher.clone(),226 );227 let pool = sc_transaction_pool::BasicPool::with_revalidation_type(228 builder.config().transaction_pool.clone(),229 Arc::new(pool_api),230 builder.prometheus_registry(),231 sc_transaction_pool::RevalidationType::Light,232 );233 Ok(pool)234 })?235 .with_import_queue_and_fprb(|236 _config,237 client,238 backend,239 fetcher,240 _select_chain,241 _tx_pool,242 spawn_task_handle,243 prometheus_registry,244 | {245 let fetch_checker = fetcher246 .map(|fetcher| fetcher.checker().clone())247 .ok_or_else(|| "Trying to start light import queue without active fetch checker")?;248 let grandpa_block_import = sc_finality_grandpa::light_block_import(249 client.clone(),250 backend,251 &(client.clone() as Arc<_>),252 Arc::new(fetch_checker),253 )?;254 let finality_proof_import = grandpa_block_import.clone();255 let finality_proof_request_builder =256 finality_proof_import.create_finality_proof_request_builder();257258 let import_queue = sc_consensus_aura::import_queue::<_, _, _, AuraPair, _>(259 sc_consensus_aura::slot_duration(&*client)?,260 grandpa_block_import,261 None,262 Some(Box::new(finality_proof_import)),263 client,264 inherent_data_providers.clone(),265 spawn_task_handle,266 prometheus_registry,267 )?;268269 Ok((import_queue, finality_proof_request_builder))270 })?271 .with_finality_proof_provider(|client, backend| {272 273 let provider = client as Arc<dyn StorageAndProofProvider<_, _>>;274 Ok(Arc::new(GrandpaFinalityProofProvider::new(backend, provider)) as _)275 })?276 .build_light()277}