diff --git a/libp2p-host/Cargo.toml b/libp2p-host/Cargo.toml new file mode 100644 index 00000000..41348a5c --- /dev/null +++ b/libp2p-host/Cargo.toml @@ -0,0 +1,10 @@ +[package] +name = "libp2p-host" +version = "0.1.0" +authors = ["Parity Technologies "] + +[dependencies] +multiaddr = "0.2.0" +futures = "0.1" +tokio-io = "0.1" +libp2p-transport = { path = "../libp2p-transport" } \ No newline at end of file diff --git a/libp2p-host/src/lib.rs b/libp2p-host/src/lib.rs new file mode 100644 index 00000000..fd09b1f6 --- /dev/null +++ b/libp2p-host/src/lib.rs @@ -0,0 +1,88 @@ +//! "Host" abstraction for transports, listener addresses, peer store. + +extern crate futures; +extern crate libp2p_transport as transport; + +use futures::{Future, IntoFuture, BoxFuture}; +use transport::{ProtocolId, MultiAddr, Socket}; + +/// Produces a future for each incoming `Socket`. +pub trait Handler { + type Future: IntoFuture; + + /// Handle the incoming socket, producing a future which should resolve + /// when the handler is finished. + fn handle(&self, socket: S) -> Self::Future; + fn boxed(self) -> BoxHandler where + Self: Sized + Send + 'static, + ::Future: Send + 'static + { + BoxHandler(Box::new(move |socket| + self.handle(socket).into_future().boxed() + )) + } +} + +impl Handler for F + where F: Fn(S) -> U, U: IntoFuture +{ + type Future = U; + + fn handle(&self, socket: S) -> U { (self)(socket) } +} + +/// A boxed handler. +pub struct BoxHandler(Box>>); + +impl Handler for BoxHandler { + type Future = BoxFuture<(), ()>; + + fn handle(&self, socket: S) -> Self::Future { + self.0.handle(socket) + } +} + +/// Multiplexes sockets onto handlers by protocol-id. +pub trait Mux: Sync { + /// The socket type this manages. + type Socket: Socket; + + /// Attach an incoming socket. + fn push(&self, socket: Self::Socket); + + /// Set the socket handler for a given protocol id. + fn set_handler(&self, proto: ProtocolId, handler: BoxHandler); + + /// Remove the socket handler for the given protocol id, returning the old handler if it existed. + fn remove_handler(&self, proto: &ProtocolId) -> Option>; +} + +/// Unimplemented. Maps peer IDs to connected addresses, protocols, and data. +pub trait PeerStore {} + +/// This is a common abstraction over the low-level bits of libp2p. +/// +/// It handles connecting over, adding and removing transports, +/// wraps an arbitrary event loop, and manages protocol IDs. +pub trait Host { + type Socket: Socket; + + /// Get a handle to the peer store. + fn peer_store(&self) -> &PeerStore; + + /// Get a handle to the underlying muxer. + fn mux(&self) -> &Mux; + + /// Set the socket handler for a given protocol id. + fn set_handler(&self, proto: ProtocolId, handler: BoxHandler) { + self.mux().set_handler(proto, handler); + } + + /// Remove the socket handler for the given protocol id, returning the old handler if it existed. + fn remove_handler(&self, proto: &ProtocolId) -> Option> { + self.mux().remove_handler(proto) + } + + /// Addresses we're listening on. + fn listen_addrs(&self) -> Vec; +} \ No newline at end of file