mirror of
https://github.com/fluencelabs/rust-libp2p
synced 2025-06-26 16:21:39 +00:00
refactor(swarm): express dial logic linearly (#3253)
Previously, the logic within `Swarm::dial` involved fairly convoluted `match` expressions. This patch refactors this function to use new utility functions introduced on `DialOpts` to handle one concern at a time. This has the advantage that we are covering slightly more cases now. Because we are parsing the `PeerId` only once at the top, checks like banning will now also act on dials that specify the `PeerId` as part of the `/p2p` protocol.
This commit is contained in:
@ -20,6 +20,8 @@
|
||||
// DEALINGS IN THE SOFTWARE.
|
||||
|
||||
use libp2p_core::connection::Endpoint;
|
||||
use libp2p_core::multiaddr::Protocol;
|
||||
use libp2p_core::multihash::Multihash;
|
||||
use libp2p_core::{Multiaddr, PeerId};
|
||||
use std::num::NonZeroU8;
|
||||
|
||||
@ -79,6 +81,104 @@ impl DialOpts {
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(_)) => None,
|
||||
}
|
||||
}
|
||||
|
||||
/// Retrieves the [`PeerId`] from the [`DialOpts`] if specified or otherwise tries to parse it
|
||||
/// from the multihash in the `/p2p` part of the address, if present.
|
||||
///
|
||||
/// Note: A [`Multiaddr`] with something else other than a [`PeerId`] within the `/p2p` protocol is invalid as per specification.
|
||||
/// Unfortunately, we are not making good use of the type system here.
|
||||
/// Really, this function should be merged with [`DialOpts::get_peer_id`] above.
|
||||
/// If it weren't for the parsing error, the function signatures would be the same.
|
||||
///
|
||||
/// See <https://github.com/multiformats/rust-multiaddr/issues/73>.
|
||||
pub(crate) fn get_or_parse_peer_id(&self) -> Result<Option<PeerId>, Multihash> {
|
||||
match self {
|
||||
DialOpts(Opts::WithPeerId(WithPeerId { peer_id, .. })) => Ok(Some(*peer_id)),
|
||||
DialOpts(Opts::WithPeerIdWithAddresses(WithPeerIdWithAddresses {
|
||||
peer_id, ..
|
||||
})) => Ok(Some(*peer_id)),
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(WithoutPeerIdWithAddress {
|
||||
address, ..
|
||||
})) => {
|
||||
let peer_id = address
|
||||
.iter()
|
||||
.last()
|
||||
.and_then(|p| {
|
||||
if let Protocol::P2p(ma) = p {
|
||||
Some(PeerId::try_from(ma))
|
||||
} else {
|
||||
None
|
||||
}
|
||||
})
|
||||
.transpose()?;
|
||||
|
||||
Ok(peer_id)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn get_addresses(&self) -> Vec<Multiaddr> {
|
||||
match self {
|
||||
DialOpts(Opts::WithPeerId(WithPeerId { .. })) => vec![],
|
||||
DialOpts(Opts::WithPeerIdWithAddresses(WithPeerIdWithAddresses {
|
||||
addresses, ..
|
||||
})) => addresses.clone(),
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(WithoutPeerIdWithAddress {
|
||||
address, ..
|
||||
})) => vec![address.clone()],
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn extend_addresses_through_behaviour(&self) -> bool {
|
||||
match self {
|
||||
DialOpts(Opts::WithPeerId(WithPeerId { .. })) => true,
|
||||
DialOpts(Opts::WithPeerIdWithAddresses(WithPeerIdWithAddresses {
|
||||
extend_addresses_through_behaviour,
|
||||
..
|
||||
})) => *extend_addresses_through_behaviour,
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(WithoutPeerIdWithAddress { .. })) => true,
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn peer_condition(&self) -> PeerCondition {
|
||||
match self {
|
||||
DialOpts(
|
||||
Opts::WithPeerId(WithPeerId { condition, .. })
|
||||
| Opts::WithPeerIdWithAddresses(WithPeerIdWithAddresses { condition, .. }),
|
||||
) => *condition,
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(WithoutPeerIdWithAddress { .. })) => {
|
||||
PeerCondition::Always
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn dial_concurrency_override(&self) -> Option<NonZeroU8> {
|
||||
match self {
|
||||
DialOpts(Opts::WithPeerId(WithPeerId {
|
||||
dial_concurrency_factor_override,
|
||||
..
|
||||
})) => *dial_concurrency_factor_override,
|
||||
DialOpts(Opts::WithPeerIdWithAddresses(WithPeerIdWithAddresses {
|
||||
dial_concurrency_factor_override,
|
||||
..
|
||||
})) => *dial_concurrency_factor_override,
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(WithoutPeerIdWithAddress { .. })) => None,
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn role_override(&self) -> Endpoint {
|
||||
match self {
|
||||
DialOpts(Opts::WithPeerId(WithPeerId { role_override, .. })) => *role_override,
|
||||
DialOpts(Opts::WithPeerIdWithAddresses(WithPeerIdWithAddresses {
|
||||
role_override,
|
||||
..
|
||||
})) => *role_override,
|
||||
DialOpts(Opts::WithoutPeerIdWithAddress(WithoutPeerIdWithAddress {
|
||||
role_override,
|
||||
..
|
||||
})) => *role_override,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl From<Multiaddr> for DialOpts {
|
||||
|
Reference in New Issue
Block a user