diff --git a/src/client.rs b/src/client.rs index bffe730..8a4ba14 100644 --- a/src/client.rs +++ b/src/client.rs @@ -4,20 +4,27 @@ use proto::{self, Connection, WindowSize, ProtoError}; use error::Reason::*; use http::{Request, Response}; -use futures::{Future, Poll, Sink, Async, AsyncSink}; +use futures::{Future, Poll, Sink, Async, AsyncSink, AndThen, MapErr}; use tokio_io::{AsyncRead, AsyncWrite}; +use tokio_io::io::WriteAll; use bytes::{Bytes, IntoBuf}; use std::fmt; +use std::io::Error as IoError; /// In progress H2 connection binding -pub struct Handshake { - // TODO: unbox - inner: Box, Error = ConnectionError>>, +pub struct Handshake { + inner: + AndThen< + MapErr, fn(IoError) -> ConnectionError>, + Result, ConnectionError>, + fn((T, &'static [u8])) -> Result, ConnectionError> + > + } /// Marker type indicating a client peer -pub struct Client { +pub struct Client { connection: Connection, } @@ -35,7 +42,7 @@ pub struct Body { pub(crate) struct Peer; impl Client - where T: AsyncRead + AsyncWrite + 'static, + where T: AsyncRead + AsyncWrite, { pub fn handshake(io: T) -> Handshake { Client::handshake2(io) @@ -43,9 +50,8 @@ impl Client } impl Client - // TODO: Get rid of 'static - where T: AsyncRead + AsyncWrite + 'static, - B: IntoBuf + 'static, + where T: AsyncRead + AsyncWrite, + B: IntoBuf { /// Bind an H2 client connection. /// @@ -56,9 +62,9 @@ impl Client debug!("binding client connection"); - let handshake = io::write_all(io, b"PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n") - .map_err(ConnectionError::from) - .and_then(|(io, _)| { + let bind: fn((T, &'static [u8])) + -> Result, ConnectionError> = + |(io, _)| { debug!("client connection bound"); let mut framed_write = proto::framed_write(io); @@ -73,9 +79,16 @@ impl Client Ok(_) => unreachable!(), Err(e) => Err(ConnectionError::from(e)), } - }); + }; - Handshake { inner: Box::new(handshake) } + let msg: &'static [u8] = b"PRI * HTTP/2.0\r\n\r\nSM\r\n\r\n"; + let handshake = io::write_all(io, msg) + .map_err(ConnectionError::from as + fn(IoError) -> ConnectionError + ) + .and_then(bind); + + Handshake { inner: handshake } } /// Returns `Ready` when the connection can initialize a new HTTP 2.0 @@ -97,8 +110,8 @@ impl Client impl Future for Client // TODO: Get rid of 'static - where T: AsyncRead + AsyncWrite + 'static, - B: IntoBuf + 'static, + where T: AsyncRead + AsyncWrite, + B: IntoBuf, { type Item = (); type Error = ConnectionError; @@ -109,7 +122,8 @@ impl Future for Client } impl fmt::Debug for Client - where T: fmt::Debug, + where T: AsyncRead + AsyncWrite, + T: fmt::Debug, B: fmt::Debug + IntoBuf, B::Buf: fmt::Debug, { @@ -122,7 +136,8 @@ impl fmt::Debug for Client // ===== impl Handshake ===== -impl Future for Handshake { +impl Future for Handshake +where T: AsyncRead + AsyncWrite { type Item = Client; type Error = ConnectionError; @@ -132,7 +147,8 @@ impl Future for Handshake { } impl fmt::Debug for Handshake - where T: fmt::Debug, + where T: AsyncRead + AsyncWrite, + T: fmt::Debug, B: fmt::Debug + IntoBuf, B::Buf: fmt::Debug + IntoBuf, {