mirror of
https://github.com/fluencelabs/rust-libp2p
synced 2025-06-26 16:21:39 +00:00
Remove the NamesIter: Clone requirement (#663)
* Remove the NamesIter: Clone requirement * Fix concerns
This commit is contained in:
@ -76,45 +76,6 @@
|
||||
//! # }
|
||||
//! ```
|
||||
//!
|
||||
//! For a listener:
|
||||
//!
|
||||
//! ```no_run
|
||||
//! extern crate bytes;
|
||||
//! extern crate futures;
|
||||
//! extern crate multistream_select;
|
||||
//! extern crate tokio;
|
||||
//! extern crate tokio_tcp;
|
||||
//!
|
||||
//! # fn main() {
|
||||
//! use bytes::Bytes;
|
||||
//! use multistream_select::listener_select_proto;
|
||||
//! use futures::{Future, Sink, Stream};
|
||||
//! use tokio_tcp::TcpListener;
|
||||
//! use tokio::runtime::current_thread::Runtime;
|
||||
//!
|
||||
//! #[derive(Debug, Copy, Clone)]
|
||||
//! enum MyProto { Echo, Hello }
|
||||
//!
|
||||
//! let server = TcpListener::bind(&"127.0.0.1:0".parse().unwrap()).unwrap()
|
||||
//! .incoming()
|
||||
//! .from_err()
|
||||
//! .and_then(move |connec| {
|
||||
//! let protos = vec![
|
||||
//! (Bytes::from("/echo/1.0.0"), <Bytes as PartialEq>::eq, MyProto::Echo),
|
||||
//! (Bytes::from("/hello/2.5.0"), <Bytes as PartialEq>::eq, MyProto::Hello),
|
||||
//! ]
|
||||
//! .into_iter();
|
||||
//! listener_select_proto(connec, protos)
|
||||
//! })
|
||||
//! .for_each(|(proto, _connec)| {
|
||||
//! println!("new remote with {:?} negotiated", proto);
|
||||
//! Ok(())
|
||||
//! });
|
||||
//!
|
||||
//! let mut rt = Runtime::new().unwrap();
|
||||
//! let _ = rt.block_on(server).expect("failed to run server");
|
||||
//! # }
|
||||
//! ```
|
||||
|
||||
extern crate bytes;
|
||||
#[macro_use]
|
||||
|
@ -45,7 +45,7 @@ use ProtocolChoiceError;
|
||||
pub fn listener_select_proto<R, I, M, P>(inner: R, protocols: I) -> ListenerSelectFuture<R, I, P>
|
||||
where
|
||||
R: AsyncRead + AsyncWrite,
|
||||
I: Iterator<Item = (Bytes, M, P)> + Clone,
|
||||
for<'r> &'r I: IntoIterator<Item = (Bytes, M, P)>,
|
||||
M: FnMut(&Bytes, &Bytes) -> bool,
|
||||
{
|
||||
ListenerSelectFuture {
|
||||
@ -77,11 +77,11 @@ enum ListenerSelectState<R: AsyncRead + AsyncWrite, I, P> {
|
||||
|
||||
impl<R, I, M, P> Future for ListenerSelectFuture<R, I, P>
|
||||
where
|
||||
I: Iterator<Item=(Bytes, M, P)> + Clone,
|
||||
for<'r> &'r I: IntoIterator<Item=(Bytes, M, P)>,
|
||||
M: FnMut(&Bytes, &Bytes) -> bool,
|
||||
R: AsyncRead + AsyncWrite,
|
||||
{
|
||||
type Item = (P, R);
|
||||
type Item = (P, R, I);
|
||||
type Error = ProtocolChoiceError;
|
||||
|
||||
fn poll(&mut self) -> Poll<Self::Item, Self::Error> {
|
||||
@ -110,7 +110,7 @@ where
|
||||
match msg {
|
||||
Some(DialerToListenerMessage::ProtocolsListRequest) => {
|
||||
let msg = ListenerToDialerMessage::ProtocolsListResponse {
|
||||
list: protocols.clone().map(|(p, _, _)| p).collect(),
|
||||
list: protocols.into_iter().map(|(p, _, _)| p).collect(),
|
||||
};
|
||||
trace!("protocols list response: {:?}", msg);
|
||||
let sender = listener.send(msg);
|
||||
@ -123,7 +123,7 @@ where
|
||||
Some(DialerToListenerMessage::ProtocolRequest { name }) => {
|
||||
let mut outcome = None;
|
||||
let mut send_back = ListenerToDialerMessage::NotAvailable;
|
||||
for (supported, mut matches, value) in protocols.clone() {
|
||||
for (supported, mut matches, value) in &protocols {
|
||||
if matches(&name, &supported) {
|
||||
send_back = ListenerToDialerMessage::ProtocolAck {name: name.clone()};
|
||||
outcome = Some(value);
|
||||
@ -149,7 +149,7 @@ where
|
||||
}
|
||||
};
|
||||
if let Some(p) = outcome {
|
||||
return Ok(Async::Ready((p, listener.into_inner())))
|
||||
return Ok(Async::Ready((p, listener.into_inner(), protocols)))
|
||||
} else {
|
||||
let stream = listener.into_future();
|
||||
self.inner = ListenerSelectState::Incoming { stream, protocols }
|
||||
|
@ -35,6 +35,19 @@ use protocol::{Dialer, DialerToListenerMessage, Listener, ListenerToDialerMessag
|
||||
use ProtocolChoiceError;
|
||||
use {dialer_select_proto, listener_select_proto};
|
||||
|
||||
/// Holds a `Vec` and satifies the iterator requirements of `listener_select_proto`.
|
||||
struct VecRefIntoIter<T>(Vec<T>);
|
||||
|
||||
impl<'a, T> IntoIterator for &'a VecRefIntoIter<T>
|
||||
where T: Clone
|
||||
{
|
||||
type Item = T;
|
||||
type IntoIter = std::vec::IntoIter<T>;
|
||||
fn into_iter(self) -> Self::IntoIter {
|
||||
self.0.clone().into_iter()
|
||||
}
|
||||
}
|
||||
|
||||
#[test]
|
||||
fn negotiate_with_self_succeeds() {
|
||||
let listener = TcpListener::bind(&"127.0.0.1:0".parse().unwrap()).unwrap();
|
||||
@ -88,8 +101,8 @@ fn select_proto_basic() {
|
||||
let protos = vec![
|
||||
(Bytes::from("/proto1"), <Bytes as PartialEq>::eq, 0),
|
||||
(Bytes::from("/proto2"), <Bytes as PartialEq>::eq, 1),
|
||||
].into_iter();
|
||||
listener_select_proto(connec, protos).map(|r| r.0)
|
||||
];
|
||||
listener_select_proto(connec, VecRefIntoIter(protos)).map(|r| r.0)
|
||||
});
|
||||
|
||||
let client = TcpStream::connect(&listener_addr)
|
||||
@ -122,8 +135,8 @@ fn no_protocol_found() {
|
||||
let protos = vec![
|
||||
(Bytes::from("/proto1"), <Bytes as PartialEq>::eq, 1),
|
||||
(Bytes::from("/proto2"), <Bytes as PartialEq>::eq, 2),
|
||||
].into_iter();
|
||||
listener_select_proto(connec, protos).map(|r| r.0)
|
||||
];
|
||||
listener_select_proto(connec, VecRefIntoIter(protos)).map(|r| r.0)
|
||||
});
|
||||
|
||||
let client = TcpStream::connect(&listener_addr)
|
||||
@ -156,8 +169,8 @@ fn select_proto_parallel() {
|
||||
let protos = vec![
|
||||
(Bytes::from("/proto1"), <Bytes as PartialEq>::eq, 0),
|
||||
(Bytes::from("/proto2"), <Bytes as PartialEq>::eq, 1),
|
||||
].into_iter();
|
||||
listener_select_proto(connec, protos).map(|r| r.0)
|
||||
];
|
||||
listener_select_proto(connec, VecRefIntoIter(protos)).map(|r| r.0)
|
||||
});
|
||||
|
||||
let client = TcpStream::connect(&listener_addr)
|
||||
@ -191,8 +204,8 @@ fn select_proto_serial() {
|
||||
let protos = vec![
|
||||
(Bytes::from("/proto1"), <Bytes as PartialEq>::eq, 0),
|
||||
(Bytes::from("/proto2"), <Bytes as PartialEq>::eq, 1),
|
||||
].into_iter();
|
||||
listener_select_proto(connec, protos).map(|r| r.0)
|
||||
];
|
||||
listener_select_proto(connec, VecRefIntoIter(protos)).map(|r| r.0)
|
||||
});
|
||||
|
||||
let client = TcpStream::connect(&listener_addr)
|
||||
|
Reference in New Issue
Block a user