diff --git a/node/src/cli.rs b/node/src/cli.rs index 76a0a42ef1c0b7788c857faafbc4eea70e4af26a..2e21862652144ea628c9eca6aec099d4e195d7d4 100644 --- a/node/src/cli.rs +++ b/node/src/cli.rs @@ -44,6 +44,21 @@ pub struct DuniterConfigExtension { /// Public Squid graphql endpoint to gossip on the network and make available in the apps. #[arg(long)] pub public_squid: Option<String>, + + /// Public endpoints from a JSON file, using following format where `protocol` and `address` are + /// strings (value is free) : + /// + /// ```json + /// { + /// "endpoints": [ + /// { "protocol": "rpc", "address": "wss://gdev.example.com" }, + /// { "protocol": "squid", "address": "gdev.example.com/graphql/v1" }, + /// { "protocol": "other", "address": "gdev.example.com/other" } + /// ] + /// } + /// ``` + #[arg(long, value_name = "JSON_FILE_PATH")] + pub public_endpoints: Option<String>, } #[derive(Debug, clap::Subcommand)] diff --git a/node/src/endpoint_gossip/mod.rs b/node/src/endpoint_gossip/mod.rs index 3e6513e59a30ecfc3394619319399d4474a06c52..7c44f55211c620cdcfc1f45b76b5e874f95a4492 100644 --- a/node/src/endpoint_gossip/mod.rs +++ b/node/src/endpoint_gossip/mod.rs @@ -102,5 +102,5 @@ pub type DuniterEndpoints = BoundedVec<DuniterEndpoint, ConstU32<10>>; #[derive(Encode, Decode, Serialize, Deserialize, Clone, Debug, PartialEq, Eq)] pub struct Peering { - endpoints: DuniterEndpoints, + pub endpoints: DuniterEndpoints, } diff --git a/node/src/service.rs b/node/src/service.rs index 79867b0dd96a69a5af28ee456fada22f505ba0dd..35d0a8857734eccdaf4d17f25ef9e96d3fc9c39e 100644 --- a/node/src/service.rs +++ b/node/src/service.rs @@ -23,13 +23,14 @@ use crate::{ endpoint_gossip::{ rpc::state::DuniterPeeringsState, well_known_endpoint_types::{RPC, SQUID}, - DuniterEndpoint, + DuniterEndpoint, DuniterEndpoints, Peering, }, rpc::DuniterPeeringRpcModuleDeps, }; use async_io::Timer; use common_runtime::Block; use futures::{Stream, StreamExt}; +use log::error; use sc_client_api::{client::BlockBackend, Backend}; use sc_consensus_grandpa::{FinalityProofProvider, SharedVoterState}; use sc_consensus_manual_seal::{run_manual_seal, EngineCommand, ManualSealParams}; @@ -42,7 +43,7 @@ use sc_transaction_pool_api::TransactionPool; use sp_consensus_babe::inherents::InherentDataProvider; use sp_core::H256; use sp_runtime::traits::BlakeTwo256; -use std::{sync::Arc, time::Duration}; +use std::{fs, sync::Arc, time::Duration}; #[cfg(not(feature = "runtime-benchmarks"))] type HostFunctions = sp_io::SubstrateHostFunctions; @@ -729,26 +730,40 @@ where ); } - let mut duniter_endpoints = vec![]; + // Get the endpoint list from file first + let mut duniter_endpoints: DuniterEndpoints = match duniter_options.public_endpoints { + None => DuniterEndpoints::truncate_from(vec![]), + Some(path) => fs::read_to_string(path) + .map(|s| { + serde_json::from_str::<Peering>(&s).expect("Failed to parse Duniter endpoints") + }) + .map(|p| p.endpoints) + .expect("Failed to read Duniter endpoints"), + }; + // Then add through the specific options if let Some(rpc_endoint) = duniter_options.public_rpc { - duniter_endpoints.push(DuniterEndpoint { - protocol: RPC.into(), - address: rpc_endoint, - }); + if duniter_endpoints + .try_push(DuniterEndpoint { + protocol: RPC.into(), + address: rpc_endoint, + }) + .is_err() + { + error!("Could not add RPC endpoint, too much endpoints already"); + } } if let Some(squid_endoint) = duniter_options.public_squid { - duniter_endpoints.push(DuniterEndpoint { - protocol: SQUID.into(), - address: squid_endoint, - }); + if duniter_endpoints + .try_push(DuniterEndpoint { + protocol: SQUID.into(), + address: squid_endoint, + }) + .is_err() + { + error!("Could not add SQUID endpoint, too much endpoints already"); + } } - let duniter_endpoints = match duniter_endpoints.try_into() { - Ok(endpoints) => endpoints, - Err(_) => { - return Err("Too much Duniter endpoints".into()); - } - }; task_manager.spawn_handle().spawn_blocking( "duniter-endpoint-gossip-handler", Some("networking"),