mirror of
https://github.com/fluencelabs/rust-libp2p
synced 2025-06-14 18:41:22 +00:00
swarm/: Improve NetworkBehaviour
documentation (#2361)
- Contrast `NetworkBehaviour` and `Transport`. - Describe hierarchy of `NetworkBehaviour` implementations. - Describe `NetworkBehaviour` combinators. - Describe `NetworkBehaviour` derive macro. - Document `out_event` mechanism`. - Document `ignore` mechanism.
This commit is contained in:
@ -22,6 +22,6 @@ futures-timer = "3.0.2"
|
|||||||
instant = "0.1.11"
|
instant = "0.1.11"
|
||||||
|
|
||||||
[dev-dependencies]
|
[dev-dependencies]
|
||||||
libp2p = { path = "../", default-features = false, features = ["yamux", "plaintext"] }
|
libp2p = { path = "../", default-features = false, features = ["identify", "ping", "plaintext", "yamux"] }
|
||||||
quickcheck = "0.9.0"
|
quickcheck = "0.9.0"
|
||||||
rand = "0.7.2"
|
rand = "0.7.2"
|
||||||
|
@ -31,18 +31,48 @@ use std::{task::Context, task::Poll};
|
|||||||
type THandlerInEvent<THandler> =
|
type THandlerInEvent<THandler> =
|
||||||
<<THandler as IntoProtocolsHandler>::Handler as ProtocolsHandler>::InEvent;
|
<<THandler as IntoProtocolsHandler>::Handler as ProtocolsHandler>::InEvent;
|
||||||
|
|
||||||
/// A behaviour for the network. Allows customizing the swarm.
|
/// A [`NetworkBehaviour`] defines the behaviour of the local node on the network.
|
||||||
///
|
///
|
||||||
/// This trait has been designed to be composable. Multiple implementations can be combined into
|
/// In contrast to [`Transport`](libp2p_core::Transport) which defines **how** to send bytes on the
|
||||||
/// one that handles all the behaviours at once.
|
/// network, [`NetworkBehaviour`] defines **what** bytes to send and **to whom**.
|
||||||
///
|
///
|
||||||
/// # Deriving `NetworkBehaviour`
|
/// Each protocol (e.g. `libp2p-ping`, `libp2p-identify` or `libp2p-kad`) implements
|
||||||
|
/// [`NetworkBehaviour`]. Multiple implementations of [`NetworkBehaviour`] can be composed into a
|
||||||
|
/// hierarchy of [`NetworkBehaviour`]s where parent implementations delegate to child
|
||||||
|
/// implementations. Finally the root of the [`NetworkBehaviour`] hierarchy is passed to
|
||||||
|
/// [`Swarm`](crate::Swarm) where it can then control the behaviour of the local node on a libp2p
|
||||||
|
/// network.
|
||||||
///
|
///
|
||||||
/// Crate users can implement this trait by using the the `#[derive(NetworkBehaviour)]`
|
/// # Hierarchy of [`NetworkBehaviour`]
|
||||||
|
///
|
||||||
|
/// To compose multiple [`NetworkBehaviour`] implementations into a single [`NetworkBehaviour`]
|
||||||
|
/// implementation, potentially building a multi-level hierarchy of [`NetworkBehaviour`]s, one can
|
||||||
|
/// use one of the [`NetworkBehaviour`] combinators, and/or use the [`NetworkBehaviour`] derive
|
||||||
|
/// macro.
|
||||||
|
///
|
||||||
|
/// ## Combinators
|
||||||
|
///
|
||||||
|
/// [`NetworkBehaviour`] combinators wrap one or more [`NetworkBehaviour`] implementations and
|
||||||
|
/// implement [`NetworkBehaviour`] themselves. Example is the [`Toggle`](crate::toggle::Toggle)
|
||||||
|
/// [`NetworkBehaviour`].
|
||||||
|
///
|
||||||
|
/// ``` rust
|
||||||
|
/// # use libp2p_swarm::DummyBehaviour;
|
||||||
|
/// # use libp2p_swarm::toggle::Toggle;
|
||||||
|
/// let my_behaviour = DummyBehaviour::default();
|
||||||
|
/// let my_toggled_behaviour = Toggle::from(Some(my_behaviour));
|
||||||
|
/// ```
|
||||||
|
///
|
||||||
|
/// ## Derive Macro
|
||||||
|
///
|
||||||
|
/// One can derive [`NetworkBehaviour`] for a custom `struct` via the `#[derive(NetworkBehaviour)]`
|
||||||
/// proc macro re-exported by the `libp2p` crate. The macro generates a delegating `trait`
|
/// proc macro re-exported by the `libp2p` crate. The macro generates a delegating `trait`
|
||||||
/// implementation for the `struct`, which delegates method calls to all struct members.
|
/// implementation for the custom `struct`. Each [`NetworkBehaviour`] trait method is simply
|
||||||
///
|
/// delegated to each `struct` member in the order the `struct` is defined. For example for
|
||||||
/// Struct members that don't implement [`NetworkBehaviour`] must be annotated with `#[behaviour(ignore)]`.
|
/// [`NetworkBehaviour::poll`] it will first poll the first `struct` member until it returns
|
||||||
|
/// [`Poll::Pending`] before moving on to later members. For [`NetworkBehaviour::addresses_of_peer`]
|
||||||
|
/// it will delegate to each `struct` member and return a concatenated array of all addresses
|
||||||
|
/// returned by the struct members.
|
||||||
///
|
///
|
||||||
/// By default the derive sets the [`NetworkBehaviour::OutEvent`] as `()` but this can be overridden
|
/// By default the derive sets the [`NetworkBehaviour::OutEvent`] as `()` but this can be overridden
|
||||||
/// with `#[behaviour(out_event = "AnotherType")]`.
|
/// with `#[behaviour(out_event = "AnotherType")]`.
|
||||||
@ -50,7 +80,72 @@ type THandlerInEvent<THandler> =
|
|||||||
/// When setting a custom `out_event` users have to implement [`From`] converting from each of the
|
/// When setting a custom `out_event` users have to implement [`From`] converting from each of the
|
||||||
/// event types generated by the struct members to the custom `out_event`.
|
/// event types generated by the struct members to the custom `out_event`.
|
||||||
///
|
///
|
||||||
/// Alternatively, users can specify `#[behaviour(event_process = true)]`. Events generated by the
|
/// ``` rust
|
||||||
|
/// # use libp2p::identify::{Identify, IdentifyEvent};
|
||||||
|
/// # use libp2p::ping::{Ping, PingEvent};
|
||||||
|
/// # use libp2p::NetworkBehaviour;
|
||||||
|
/// #[derive(NetworkBehaviour)]
|
||||||
|
/// #[behaviour(out_event = "Event")]
|
||||||
|
/// struct MyBehaviour {
|
||||||
|
/// identify: Identify,
|
||||||
|
/// ping: Ping,
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// enum Event {
|
||||||
|
/// Identify(IdentifyEvent),
|
||||||
|
/// Ping(PingEvent),
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// impl From<IdentifyEvent> for Event {
|
||||||
|
/// fn from(event: IdentifyEvent) -> Self {
|
||||||
|
/// Self::Identify(event)
|
||||||
|
/// }
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// impl From<PingEvent> for Event {
|
||||||
|
/// fn from(event: PingEvent) -> Self {
|
||||||
|
/// Self::Ping(event)
|
||||||
|
/// }
|
||||||
|
/// }
|
||||||
|
/// ```
|
||||||
|
///
|
||||||
|
/// Struct members that don't implement [`NetworkBehaviour`] must be annotated with
|
||||||
|
/// `#[behaviour(ignore)]`.
|
||||||
|
///
|
||||||
|
/// ``` rust
|
||||||
|
/// # use libp2p::identify::{Identify, IdentifyEvent};
|
||||||
|
/// # use libp2p::ping::{Ping, PingEvent};
|
||||||
|
/// # use libp2p::NetworkBehaviour;
|
||||||
|
/// #[derive(NetworkBehaviour)]
|
||||||
|
/// #[behaviour(out_event = "Event")]
|
||||||
|
/// struct MyBehaviour {
|
||||||
|
/// identify: Identify,
|
||||||
|
/// ping: Ping,
|
||||||
|
///
|
||||||
|
/// #[behaviour(ignore)]
|
||||||
|
/// some_string: String,
|
||||||
|
/// }
|
||||||
|
/// #
|
||||||
|
/// # enum Event {
|
||||||
|
/// # Identify(IdentifyEvent),
|
||||||
|
/// # Ping(PingEvent),
|
||||||
|
/// # }
|
||||||
|
/// #
|
||||||
|
/// # impl From<IdentifyEvent> for Event {
|
||||||
|
/// # fn from(event: IdentifyEvent) -> Self {
|
||||||
|
/// # Self::Identify(event)
|
||||||
|
/// # }
|
||||||
|
/// # }
|
||||||
|
/// #
|
||||||
|
/// # impl From<PingEvent> for Event {
|
||||||
|
/// # fn from(event: PingEvent) -> Self {
|
||||||
|
/// # Self::Ping(event)
|
||||||
|
/// # }
|
||||||
|
/// # }
|
||||||
|
/// ```
|
||||||
|
///
|
||||||
|
/// For users that need access to the root [`NetworkBehaviour`] implementation while processing
|
||||||
|
/// emitted events, one can specify `#[behaviour(event_process = true)]`. Events generated by the
|
||||||
/// struct members are delegated to [`NetworkBehaviourEventProcess`] implementations. Those must be
|
/// struct members are delegated to [`NetworkBehaviourEventProcess`] implementations. Those must be
|
||||||
/// provided by the user on the type that [`NetworkBehaviour`] is derived on.
|
/// provided by the user on the type that [`NetworkBehaviour`] is derived on.
|
||||||
///
|
///
|
||||||
|
Reference in New Issue
Block a user