litep2p/transport/
mod.rs

1// Copyright 2023 litep2p developers
2//
3// Permission is hereby granted, free of charge, to any person obtaining a
4// copy of this software and associated documentation files (the "Software"),
5// to deal in the Software without restriction, including without limitation
6// the rights to use, copy, modify, merge, publish, distribute, sublicense,
7// and/or sell copies of the Software, and to permit persons to whom the
8// Software is furnished to do so, subject to the following conditions:
9//
10// The above copyright notice and this permission notice shall be included in
11// all copies or substantial portions of the Software.
12//
13// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
14// OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
18// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
19// DEALINGS IN THE SOFTWARE.
20
21//! Transport protocol implementations provided by [`Litep2p`](`crate::Litep2p`).
22
23use crate::{error::DialError, transport::manager::TransportHandle, types::ConnectionId, PeerId};
24
25use futures::Stream;
26use hickory_resolver::TokioResolver;
27use multiaddr::Multiaddr;
28
29use std::{fmt::Debug, sync::Arc, time::Duration};
30
31pub(crate) mod common;
32#[cfg(feature = "quic")]
33pub mod quic;
34pub mod tcp;
35#[cfg(feature = "webrtc")]
36pub mod webrtc;
37#[cfg(feature = "websocket")]
38pub mod websocket;
39
40#[cfg(test)]
41pub(crate) mod dummy;
42
43pub(crate) mod manager;
44
45pub use manager::limits::{ConnectionLimitsConfig, ConnectionLimitsError};
46
47/// Timeout for opening a connection.
48pub(crate) const CONNECTION_OPEN_TIMEOUT: Duration = Duration::from_secs(10);
49
50/// Timeout for opening a substream.
51pub(crate) const SUBSTREAM_OPEN_TIMEOUT: Duration = Duration::from_secs(5);
52
53/// Timeout for connection waiting new substreams.
54pub(crate) const KEEP_ALIVE_TIMEOUT: Duration = Duration::from_secs(5);
55
56/// Maximum number of parallel dial attempts.
57pub(crate) const MAX_PARALLEL_DIALS: usize = 8;
58
59/// Connection endpoint.
60#[derive(Debug, Clone, PartialEq, Eq)]
61pub enum Endpoint {
62    /// Successfully established outbound connection.
63    Dialer {
64        /// Address that was dialed.
65        address: Multiaddr,
66
67        /// Connection ID.
68        connection_id: ConnectionId,
69    },
70
71    /// Successfully established inbound connection.
72    Listener {
73        /// Local connection address.
74        address: Multiaddr,
75
76        /// Connection ID.
77        connection_id: ConnectionId,
78    },
79}
80
81impl Endpoint {
82    /// Get `Multiaddr` of the [`Endpoint`].
83    pub fn address(&self) -> &Multiaddr {
84        match self {
85            Self::Dialer { address, .. } => address,
86            Self::Listener { address, .. } => address,
87        }
88    }
89
90    /// Crate dialer.
91    pub(crate) fn dialer(address: Multiaddr, connection_id: ConnectionId) -> Self {
92        Endpoint::Dialer {
93            address,
94            connection_id,
95        }
96    }
97
98    /// Create listener.
99    pub(crate) fn listener(address: Multiaddr, connection_id: ConnectionId) -> Self {
100        Endpoint::Listener {
101            address,
102            connection_id,
103        }
104    }
105
106    /// Get `ConnectionId` of the `Endpoint`.
107    pub fn connection_id(&self) -> ConnectionId {
108        match self {
109            Self::Dialer { connection_id, .. } => *connection_id,
110            Self::Listener { connection_id, .. } => *connection_id,
111        }
112    }
113
114    /// Is this a listener endpoint?
115    pub fn is_listener(&self) -> bool {
116        std::matches!(self, Self::Listener { .. })
117    }
118}
119
120/// Transport event.
121#[derive(Debug)]
122pub(crate) enum TransportEvent {
123    /// Fully negotiated connection established to remote peer.
124    ConnectionEstablished {
125        /// Peer ID.
126        peer: PeerId,
127
128        /// Endpoint.
129        endpoint: Endpoint,
130    },
131
132    PendingInboundConnection {
133        /// Connection ID.
134        connection_id: ConnectionId,
135    },
136
137    /// Connection opened to remote but not yet negotiated.
138    ConnectionOpened {
139        /// Connection ID.
140        connection_id: ConnectionId,
141
142        /// Address that was dialed.
143        address: Multiaddr,
144    },
145
146    /// Connection closed to remote peer.
147    #[allow(unused)]
148    ConnectionClosed {
149        /// Peer ID.
150        peer: PeerId,
151
152        /// Connection ID.
153        connection_id: ConnectionId,
154    },
155
156    /// Failed to dial remote peer.
157    DialFailure {
158        /// Connection ID.
159        connection_id: ConnectionId,
160
161        /// Dialed address.
162        address: Multiaddr,
163
164        /// Error.
165        error: DialError,
166    },
167
168    /// Open failure for an unnegotiated set of connections.
169    OpenFailure {
170        /// Connection ID.
171        connection_id: ConnectionId,
172
173        /// Errors.
174        errors: Vec<(Multiaddr, DialError)>,
175    },
176}
177
178pub(crate) trait TransportBuilder {
179    type Config: Debug;
180    type Transport: Transport;
181
182    /// Create new [`Transport`] object.
183    fn new(
184        context: TransportHandle,
185        config: Self::Config,
186        resolver: Arc<TokioResolver>,
187    ) -> crate::Result<(Self, Vec<Multiaddr>)>
188    where
189        Self: Sized;
190}
191
192pub(crate) trait Transport: Stream + Unpin + Send {
193    /// Dial `address` and negotiate connection.
194    fn dial(&mut self, connection_id: ConnectionId, address: Multiaddr) -> crate::Result<()>;
195
196    /// Accept negotiated connection.
197    fn accept(&mut self, connection_id: ConnectionId) -> crate::Result<()>;
198
199    /// Accept pending connection.
200    fn accept_pending(&mut self, connection_id: ConnectionId) -> crate::Result<()>;
201
202    /// Reject pending connection.
203    fn reject_pending(&mut self, connection_id: ConnectionId) -> crate::Result<()>;
204
205    /// Reject negotiated connection.
206    fn reject(&mut self, connection_id: ConnectionId) -> crate::Result<()>;
207
208    /// Attempt to open connection to remote peer over one or more addresses.
209    fn open(&mut self, connection_id: ConnectionId, addresses: Vec<Multiaddr>)
210        -> crate::Result<()>;
211
212    /// Negotiate opened connection.
213    fn negotiate(&mut self, connection_id: ConnectionId) -> crate::Result<()>;
214
215    /// Cancel opening connections.
216    ///
217    /// This is a no-op for connections that have already succeeded/canceled.
218    fn cancel(&mut self, connection_id: ConnectionId);
219}