From c6addc9bd52a736d648c1b3d8d858c4e0d2bacdb Mon Sep 17 00:00:00 2001
From: Arkadiy Paronyan <arkady.paronyan@gmail.com>
Date: Mon, 25 Mar 2019 11:28:35 +0100
Subject: [PATCH] CLI option to enable authoring when offline (#2104)

* CLI option to enable authoring when offline

* Update core/service/src/config.rs

Co-Authored-By: arkpar <arkady.paronyan@gmail.com>
---
 substrate/core/cli/src/lib.rs            |  2 ++
 substrate/core/cli/src/params.rs         |  4 ++++
 substrate/core/consensus/aura/src/lib.rs | 22 +++++++++++++++++++---
 substrate/core/service/src/config.rs     |  3 +++
 substrate/core/service/test/src/lib.rs   |  1 +
 substrate/node-template/src/service.rs   |  1 +
 substrate/node/cli/src/service.rs        |  1 +
 7 files changed, 31 insertions(+), 3 deletions(-)

diff --git a/substrate/core/cli/src/lib.rs b/substrate/core/cli/src/lib.rs
index 1868d79d746..dd47fb73bda 100644
--- a/substrate/core/cli/src/lib.rs
+++ b/substrate/core/cli/src/lib.rs
@@ -470,6 +470,8 @@ where
 		config.telemetry_endpoints = Some(TelemetryEndpoints::new(cli.telemetry_endpoints));
 	}
 
+	config.force_authoring = cli.force_authoring;
+
 	Ok(config)
 }
 
diff --git a/substrate/core/cli/src/params.rs b/substrate/core/cli/src/params.rs
index d84f202501c..21ceafa20f6 100644
--- a/substrate/core/cli/src/params.rs
+++ b/substrate/core/cli/src/params.rs
@@ -325,6 +325,10 @@ pub struct RunCmd {
 	#[allow(missing_docs)]
 	#[structopt(flatten)]
 	pub keyring: Keyring,
+
+	/// Enable authoring even when offline.
+	#[structopt(long = "force-authoring")]
+	pub force_authoring: bool,
 }
 
 /// Stores all required Cli values for a keyring test account.
diff --git a/substrate/core/consensus/aura/src/lib.rs b/substrate/core/consensus/aura/src/lib.rs
index e2c1091f14a..3a9bfd971ab 100644
--- a/substrate/core/consensus/aura/src/lib.rs
+++ b/substrate/core/consensus/aura/src/lib.rs
@@ -160,6 +160,7 @@ pub fn start_aura_thread<B, C, E, I, P, SO, Error, OnExit>(
 	sync_oracle: SO,
 	on_exit: OnExit,
 	inherent_data_providers: InherentDataProviders,
+	force_authoring: bool,
 ) -> Result<(), consensus_common::Error> where
 	B: Block + 'static,
 	C: Authorities<B> + ChainHead<B> + Send + Sync + 'static,
@@ -176,7 +177,13 @@ pub fn start_aura_thread<B, C, E, I, P, SO, Error, OnExit>(
 	Error: ::std::error::Error + Send + From<::consensus_common::Error> + 'static,
 {
 	let worker = AuraWorker {
-		client: client.clone(), block_import, env, local_key, inherent_data_providers: inherent_data_providers.clone(), sync_oracle: sync_oracle.clone(),
+		client: client.clone(),
+		block_import,
+		env,
+		local_key,
+		inherent_data_providers: inherent_data_providers.clone(),
+		sync_oracle: sync_oracle.clone(),
+		force_authoring,
 	};
 
 	aura_slots::start_slot_worker_thread::<_, _, _, _, AuraSlotCompatible, _>(
@@ -199,6 +206,7 @@ pub fn start_aura<B, C, E, I, P, SO, Error, OnExit>(
 	sync_oracle: SO,
 	on_exit: OnExit,
 	inherent_data_providers: InherentDataProviders,
+	force_authoring: bool,
 ) -> Result<impl Future<Item=(), Error=()>, consensus_common::Error> where
 	B: Block,
 	C: Authorities<B> + ChainHead<B>,
@@ -215,7 +223,13 @@ pub fn start_aura<B, C, E, I, P, SO, Error, OnExit>(
 	OnExit: Future<Item=(), Error=()>,
 {
 	let worker = AuraWorker {
-		client: client.clone(), block_import, env, local_key, inherent_data_providers: inherent_data_providers.clone(), sync_oracle: sync_oracle.clone(),
+		client: client.clone(),
+		block_import,
+		env,
+		local_key,
+		inherent_data_providers: inherent_data_providers.clone(),
+		sync_oracle: sync_oracle.clone(),
+		force_authoring,
 	};
 	aura_slots::start_slot_worker::<_, _, _, _, AuraSlotCompatible, _>(
 		slot_duration,
@@ -234,6 +248,7 @@ struct AuraWorker<C, E, I, P, SO> {
 	local_key: Arc<P>,
 	sync_oracle: SO,
 	inherent_data_providers: InherentDataProviders,
+	force_authoring: bool,
 }
 
 impl<B: Block, C, E, I, P, Error, SO> SlotWorker<B> for AuraWorker<C, E, I, P, SO> where
@@ -287,7 +302,7 @@ impl<B: Block, C, E, I, P, Error, SO> SlotWorker<B> for AuraWorker<C, E, I, P, S
 			}
 		};
 
-		if self.sync_oracle.is_offline() && authorities.len() > 1 {
+		if !self.force_authoring && self.sync_oracle.is_offline() && authorities.len() > 1 {
 			debug!(target: "aura", "Skipping proposal slot. Waiting for the network.");
 			telemetry!(CONSENSUS_DEBUG; "aura.skipping_proposal_slot";
 				"authorities_len" => authorities.len()
@@ -808,6 +823,7 @@ mod tests {
 				DummyOracle,
 				futures::empty(),
 				inherent_data_providers,
+				false,
 			).expect("Starts aura");
 
 			runtime.spawn(aura);
diff --git a/substrate/core/service/src/config.rs b/substrate/core/service/src/config.rs
index d61f5a23845..e7503d0ad2c 100644
--- a/substrate/core/service/src/config.rs
+++ b/substrate/core/service/src/config.rs
@@ -68,6 +68,8 @@ pub struct Configuration<C, G: Serialize + DeserializeOwned + BuildStorage> {
 	pub telemetry_endpoints: Option<TelemetryEndpoints>,
 	/// The default number of 64KB pages to allocate for Wasm execution
 	pub default_heap_pages: Option<u64>,
+	/// Enable authoring even when offline.
+	pub force_authoring: bool,
 }
 
 impl<C: Default, G: Serialize + DeserializeOwned + BuildStorage> Configuration<C, G> {
@@ -93,6 +95,7 @@ impl<C: Default, G: Serialize + DeserializeOwned + BuildStorage> Configuration<C
 			rpc_ws: None,
 			telemetry_endpoints: None,
 			default_heap_pages: None,
+			force_authoring: false,
 		};
 		configuration.network.boot_nodes = configuration.chain_spec.boot_nodes().to_vec();
 
diff --git a/substrate/core/service/test/src/lib.rs b/substrate/core/service/test/src/lib.rs
index 72372f9292a..c6e13616720 100644
--- a/substrate/core/service/test/src/lib.rs
+++ b/substrate/core/service/test/src/lib.rs
@@ -120,6 +120,7 @@ fn node_config<F: ServiceFactory> (
 		rpc_ws: None,
 		telemetry_endpoints: None,
 		default_heap_pages: None,
+		force_authoring: false,
 	}
 }
 
diff --git a/substrate/node-template/src/service.rs b/substrate/node-template/src/service.rs
index ae98d01de41..5f1a3751816 100644
--- a/substrate/node-template/src/service.rs
+++ b/substrate/node-template/src/service.rs
@@ -73,6 +73,7 @@ construct_service_factory! {
 						service.network(),
 						service.on_exit(),
 						service.config.custom.inherent_data_providers.clone(),
+						service.config.force_authoring,
 					)?);
 				}
 
diff --git a/substrate/node/cli/src/service.rs b/substrate/node/cli/src/service.rs
index bd1b89f0e60..b65dbc74442 100644
--- a/substrate/node/cli/src/service.rs
+++ b/substrate/node/cli/src/service.rs
@@ -97,6 +97,7 @@ construct_service_factory! {
 						service.network(),
 						service.on_exit(),
 						service.config.custom.inherent_data_providers.clone(),
+						service.config.force_authoring,
 					)?);
 
 					info!("Running Grandpa session as Authority {}", key.public());
-- 
GitLab