swarm: Split off "keep alive" functionality from DummyConnectionHandler (#2859)

Previously, the `DummyConnectionHandler` offered a "keep alive" functionality,
i.e. it allowed users to set the value of what is returned from
`ConnectionHandler::keep_alive`. This handler is primarily used in tests or
`NetworkBehaviour`s that don't open any connections (like mDNS). In all of these
cases, it is statically known whether we want to keep connections alive. As
such, this functionality is better represented by a static
`KeepAliveConnectionHandler` that always returns `KeepAlive::Yes` and a
`DummyConnectionHandler` that always returns `KeepAlive::No`.

To follow the naming conventions described in
https://github.com/libp2p/rust-libp2p/issues/2217, we introduce a top-level
`keep_alive` and `dummy` behaviour in `libp2p-swarm` that contains both the
`NetworkBehaviour` and `ConnectionHandler` implementation for either case.
This commit is contained in:
Thomas Eizinger
2022-10-06 03:50:11 +11:00
committed by GitHub
parent da0403dc45
commit bdf9209824
26 changed files with 412 additions and 319 deletions

View File

@ -61,7 +61,9 @@ mod upgrade;
pub mod behaviour;
pub mod dial_opts;
pub mod dummy;
pub mod handler;
pub mod keep_alive;
pub use behaviour::{
CloseConnection, NetworkBehaviour, NetworkBehaviourAction, NotifyHandler, PollParameters,
@ -348,11 +350,11 @@ where
/// # use libp2p_swarm::dial_opts::{DialOpts, PeerCondition};
/// # use libp2p_core::{Multiaddr, PeerId, Transport};
/// # use libp2p_core::transport::dummy::DummyTransport;
/// # use libp2p_swarm::DummyBehaviour;
/// # use libp2p_swarm::dummy;
/// #
/// let mut swarm = Swarm::new(
/// DummyTransport::new().boxed(),
/// DummyBehaviour::default(),
/// dummy::Behaviour,
/// PeerId::random(),
/// );
///
@ -1514,58 +1516,6 @@ impl error::Error for DialError {
}
}
/// Dummy implementation of [`NetworkBehaviour`] that doesn't do anything.
#[derive(Clone)]
pub struct DummyBehaviour {
keep_alive: KeepAlive,
}
impl DummyBehaviour {
pub fn with_keep_alive(keep_alive: KeepAlive) -> Self {
Self { keep_alive }
}
pub fn keep_alive_mut(&mut self) -> &mut KeepAlive {
&mut self.keep_alive
}
}
impl Default for DummyBehaviour {
fn default() -> Self {
Self {
keep_alive: KeepAlive::No,
}
}
}
impl NetworkBehaviour for DummyBehaviour {
type ConnectionHandler = handler::DummyConnectionHandler;
type OutEvent = void::Void;
fn new_handler(&mut self) -> Self::ConnectionHandler {
handler::DummyConnectionHandler {
keep_alive: self.keep_alive,
}
}
fn inject_event(
&mut self,
_: PeerId,
_: ConnectionId,
event: <Self::ConnectionHandler as ConnectionHandler>::OutEvent,
) {
void::unreachable(event)
}
fn poll(
&mut self,
_: &mut Context<'_>,
_: &mut impl PollParameters,
) -> Poll<NetworkBehaviourAction<Self::OutEvent, Self::ConnectionHandler>> {
Poll::Pending
}
}
/// Information about the connections obtained by [`Swarm::network_info()`].
#[derive(Clone, Debug)]
pub struct NetworkInfo {
@ -1617,7 +1567,6 @@ fn p2p_addr(peer: Option<PeerId>, addr: Multiaddr) -> Result<Multiaddr, Multiadd
#[cfg(test)]
mod tests {
use super::*;
use crate::handler::DummyConnectionHandler;
use crate::test::{CallTraceBehaviour, MockBehaviour};
use futures::executor::block_on;
use futures::future::poll_fn;
@ -1714,9 +1663,7 @@ mod tests {
fn test_connect_disconnect_ban() {
// Since the test does not try to open any substreams, we can
// use the dummy protocols handler.
let handler_proto = DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
};
let handler_proto = keep_alive::ConnectionHandler;
let mut swarm1 = new_test_swarm::<_, ()>(handler_proto.clone()).build();
let mut swarm2 = new_test_swarm::<_, ()>(handler_proto).build();
@ -1834,9 +1781,7 @@ mod tests {
fn test_swarm_disconnect() {
// Since the test does not try to open any substreams, we can
// use the dummy protocols handler.
let handler_proto = DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
};
let handler_proto = keep_alive::ConnectionHandler;
let mut swarm1 = new_test_swarm::<_, ()>(handler_proto.clone()).build();
let mut swarm2 = new_test_swarm::<_, ()>(handler_proto).build();
@ -1902,9 +1847,7 @@ mod tests {
fn test_behaviour_disconnect_all() {
// Since the test does not try to open any substreams, we can
// use the dummy protocols handler.
let handler_proto = DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
};
let handler_proto = keep_alive::ConnectionHandler;
let mut swarm1 = new_test_swarm::<_, ()>(handler_proto.clone()).build();
let mut swarm2 = new_test_swarm::<_, ()>(handler_proto).build();
@ -1972,9 +1915,7 @@ mod tests {
fn test_behaviour_disconnect_one() {
// Since the test does not try to open any substreams, we can
// use the dummy protocols handler.
let handler_proto = DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
};
let handler_proto = keep_alive::ConnectionHandler;
let mut swarm1 = new_test_swarm::<_, ()>(handler_proto.clone()).build();
let mut swarm2 = new_test_swarm::<_, ()>(handler_proto).build();
@ -2059,11 +2000,9 @@ mod tests {
fn prop(concurrency_factor: DialConcurrencyFactor) {
block_on(async {
let mut swarm = new_test_swarm::<_, ()>(DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
})
.dial_concurrency_factor(concurrency_factor.0)
.build();
let mut swarm = new_test_swarm::<_, ()>(keep_alive::ConnectionHandler)
.dial_concurrency_factor(concurrency_factor.0)
.build();
// Listen on `concurrency_factor + 1` addresses.
//
@ -2129,11 +2068,9 @@ mod tests {
let outgoing_limit = rand::thread_rng().gen_range(1..10);
let limits = ConnectionLimits::default().with_max_pending_outgoing(Some(outgoing_limit));
let mut network = new_test_swarm::<_, ()>(DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
})
.connection_limits(limits)
.build();
let mut network = new_test_swarm::<_, ()>(keep_alive::ConnectionHandler)
.connection_limits(limits)
.build();
let addr: Multiaddr = "/memory/1234".parse().unwrap();
@ -2185,16 +2122,12 @@ mod tests {
fn prop(limit: Limit) {
let limit = limit.0;
let mut network1 = new_test_swarm::<_, ()>(DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
})
.connection_limits(limits(limit))
.build();
let mut network2 = new_test_swarm::<_, ()>(DummyConnectionHandler {
keep_alive: KeepAlive::Yes,
})
.connection_limits(limits(limit))
.build();
let mut network1 = new_test_swarm::<_, ()>(keep_alive::ConnectionHandler)
.connection_limits(limits(limit))
.build();
let mut network2 = new_test_swarm::<_, ()>(keep_alive::ConnectionHandler)
.connection_limits(limits(limit))
.build();
let _ = network1.listen_on(multiaddr![Memory(0u64)]).unwrap();
let listen_addr = async_std::task::block_on(poll_fn(|cx| {
@ -2299,8 +2232,8 @@ mod tests {
// Checks whether dialing an address containing the wrong peer id raises an error
// for the expected peer id instead of the obtained peer id.
let mut swarm1 = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let mut swarm2 = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let mut swarm1 = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
let mut swarm2 = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
swarm1.listen_on("/memory/0".parse().unwrap()).unwrap();
@ -2359,7 +2292,7 @@ mod tests {
//
// The last two can happen in any order.
let mut swarm = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let mut swarm = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
swarm.listen_on("/memory/0".parse().unwrap()).unwrap();
let local_address =
@ -2417,7 +2350,7 @@ mod tests {
fn dial_self_by_id() {
// Trying to dial self by passing the same `PeerId` shouldn't even be possible in the first
// place.
let swarm = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let swarm = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
let peer_id = *swarm.local_peer_id();
assert!(!swarm.is_connected(&peer_id));
}
@ -2428,7 +2361,7 @@ mod tests {
let target = PeerId::random();
let mut swarm = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let mut swarm = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
let addresses = HashSet::from([
multiaddr![Ip4([0, 0, 0, 0]), Tcp(rand::random::<u16>())],
@ -2473,8 +2406,8 @@ mod tests {
fn aborting_pending_connection_surfaces_error() {
let _ = env_logger::try_init();
let mut dialer = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let mut listener = new_test_swarm::<_, ()>(DummyConnectionHandler::default()).build();
let mut dialer = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
let mut listener = new_test_swarm::<_, ()>(dummy::ConnectionHandler).build();
let listener_peer_id = *listener.local_peer_id();
listener.listen_on(multiaddr![Memory(0u64)]).unwrap();