Skip to content
This repository was archived by the owner on Nov 15, 2023. It is now read-only.

Commit ea721a1

Browse files
authored
network: Use "one shot" protocol handler. (#3520)
* network: Use "one shot" protocol handler. Add two new `NetworkBehaviour`s, one handling remote block requests and another one to handle light client requests (both local and from remote). The change is motivated by the desire to use multiple substreams of a single connection for different protocols. To achieve this, libp2p's `OneShotHandler` is used as a protocol handler in each behaviour. It will open a fresh substream for the duration of the request and close it afterwards. For block requests, we currently only handle incoming requests from remote and tests are missing. For light client handling we support incoming requests from remote and also ported a substantial amount of functionality over from `light_dispatch.rs` (including several tests). However the result lacks in at least two aspects: (1) We require external updates w.r.t. the best block per peer and currently nothing updates this information. (2) We carry a lot of peer-related state around. Both aspects could be simplified by externalising peer selection and just requiring a specific peer ID where the request should be sent to. We still have to maintain some peer related state due to the way libp2p's swarm and network behaviour work (e.g. we must make sure to always issue `NetworkBehaviourAction::SendEvent`s to peers we are connected to, otherwise the actions die a silent death. Another change implemented here is the use of protocol buffers as the encoding for network messages. Certain individual fields of messages are still SCALE encoded. There has been some discussion about this in another PR (#3452), so far without resolution. * Uncomment `Behaviour::light_client_request`. * Add license headers.
1 parent 2723b9c commit ea721a1

File tree

11 files changed

+2436
-27
lines changed

11 files changed

+2436
-27
lines changed

Cargo.lock

Lines changed: 7 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

client/network/Cargo.toml

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,9 @@ license = "GPL-3.0"
66
authors = ["Parity Technologies <[email protected]>"]
77
edition = "2018"
88

9+
[build-dependencies]
10+
prost-build = "0.6.1"
11+
912
[dependencies]
1013
bitflags = "1.2.0"
1114
bytes = "0.5.0"
@@ -24,7 +27,9 @@ linked-hash-map = "0.5.2"
2427
linked_hash_set = "0.1.3"
2528
log = "0.4.8"
2629
lru = "0.4.0"
30+
nohash-hasher = "0.1.3"
2731
parking_lot = "0.10.0"
32+
prost = "0.6.1"
2833
rand = "0.7.2"
2934
rustc-hex = "2.0.1"
3035
sc-block-builder = { version = "0.8", path = "../block-builder" }
@@ -45,17 +50,22 @@ sp-keyring = { version = "2.0.0", optional = true, path = "../../primitives/keyr
4550
sp-runtime = { version = "2.0.0", path = "../../primitives/runtime" }
4651
substrate-test-client = { version = "2.0.0", optional = true, path = "../../test-utils/client" }
4752
substrate-test-runtime-client = { version = "2.0.0", optional = true, path = "../../test-utils/runtime/client" }
53+
thiserror = "1"
4854
unsigned-varint = { version = "0.3.0", features = ["codec"] }
4955
void = "1.0.2"
5056
zeroize = "1.0.0"
5157
yamux = "0.4.2"
5258

5359
[dev-dependencies]
60+
async-std = "1.5"
61+
assert_matches = "1.3"
5462
env_logger = "0.7.0"
5563
quickcheck = "0.9.0"
5664
rand = "0.7.2"
5765
sp-keyring = { version = "2.0.0", path = "../../primitives/keyring" }
5866
sp-test-primitives = { version = "2.0.0", path = "../../primitives/test-primitives" }
67+
substrate-test-runtime = { version = "2.0.0", path = "../../test-utils/runtime" }
68+
substrate-test-runtime-client = { version = "2.0.0", path = "../../test-utils/runtime/client" }
5969
tempfile = "3.1.0"
6070

6171
[features]

client/network/build.rs

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
const PROTOS: &[&str] = &[
2+
"src/protocol/schema/api.v1.proto",
3+
"src/protocol/schema/light.v1.proto"
4+
];
5+
6+
fn main() {
7+
prost_build::compile_protos(PROTOS, &["src/protocol"]).unwrap();
8+
}

client/network/src/behaviour.rs

Lines changed: 16 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ use crate::{
1919
Event, protocol::event::DhtEvent
2020
};
2121
use crate::{ExHashT, specialization::NetworkSpecialization};
22-
use crate::protocol::{CustomMessageOutcome, Protocol};
22+
use crate::protocol::{self, light_client_handler, CustomMessageOutcome, Protocol};
2323
use libp2p::NetworkBehaviour;
2424
use libp2p::core::{Multiaddr, PeerId, PublicKey};
2525
use libp2p::kad::record;
@@ -42,7 +42,10 @@ pub struct Behaviour<B: BlockT, S: NetworkSpecialization<B>, H: ExHashT> {
4242
debug_info: debug_info::DebugInfoBehaviour<Substream<StreamMuxerBox>>,
4343
/// Discovers nodes of the network.
4444
discovery: DiscoveryBehaviour<Substream<StreamMuxerBox>>,
45-
45+
/// Block request handling.
46+
block_requests: protocol::BlockRequests<Substream<StreamMuxerBox>, B>,
47+
/// Light client request handling.
48+
light_client_handler: protocol::LightClientHandler<Substream<StreamMuxerBox>, B>,
4649
/// Queue of events to produce for the outside.
4750
#[behaviour(ignore)]
4851
events: Vec<BehaviourOut<B>>,
@@ -66,6 +69,8 @@ impl<B: BlockT, S: NetworkSpecialization<B>, H: ExHashT> Behaviour<B, S, H> {
6669
enable_mdns: bool,
6770
allow_private_ipv4: bool,
6871
discovery_only_if_under_num: u64,
72+
block_requests: protocol::BlockRequests<Substream<StreamMuxerBox>, B>,
73+
light_client_handler: protocol::LightClientHandler<Substream<StreamMuxerBox>, B>,
6974
) -> Self {
7075
Behaviour {
7176
substrate,
@@ -77,7 +82,9 @@ impl<B: BlockT, S: NetworkSpecialization<B>, H: ExHashT> Behaviour<B, S, H> {
7782
allow_private_ipv4,
7883
discovery_only_if_under_num,
7984
).await,
80-
events: Vec::new(),
85+
block_requests,
86+
light_client_handler,
87+
events: Vec::new()
8188
}
8289
}
8390

@@ -119,6 +126,12 @@ impl<B: BlockT, S: NetworkSpecialization<B>, H: ExHashT> Behaviour<B, S, H> {
119126
pub fn put_value(&mut self, key: record::Key, value: Vec<u8>) {
120127
self.discovery.put_value(key, value);
121128
}
129+
130+
/// Issue a light client request.
131+
#[allow(unused)]
132+
pub fn light_client_request(&mut self, r: light_client_handler::Request<B>) -> Result<(), light_client_handler::Error> {
133+
self.light_client_handler.request(r)
134+
}
122135
}
123136

124137
impl<B: BlockT, S: NetworkSpecialization<B>, H: ExHashT> NetworkBehaviourEventProcess<void::Void> for

client/network/src/protocol.rs

Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -54,15 +54,30 @@ use crate::error;
5454
use util::LruHashSet;
5555
use wasm_timer::Instant;
5656

57+
// Include sources generated from protobuf definitions.
58+
pub mod api {
59+
pub mod v1 {
60+
include!(concat!(env!("OUT_DIR"), "/api.v1.rs"));
61+
pub mod light {
62+
include!(concat!(env!("OUT_DIR"), "/api.v1.light.rs"));
63+
}
64+
}
65+
}
66+
5767
mod legacy_proto;
5868
mod util;
5969

70+
pub mod block_requests;
6071
pub mod message;
6172
pub mod event;
73+
pub mod light_client_handler;
6274
pub mod light_dispatch;
6375
pub mod specialization;
6476
pub mod sync;
6577

78+
pub use block_requests::BlockRequests;
79+
pub use light_client_handler::LightClientHandler;
80+
6681
const REQUEST_TIMEOUT_SEC: u64 = 40;
6782
/// Interval at which we perform time based maintenance
6883
const TICK_TIMEOUT: time::Duration = time::Duration::from_millis(1100);

0 commit comments

Comments
 (0)