//! The `Accept` trait and supporting types. //! //! This module contains: //! //! - The [`Accept`](Accept) trait used to asynchronously accept incoming //! connections. //! - Utilities like `poll_fn` to ease creating a custom `Accept`. #[cfg(feature = "stream")] use futures_core::Stream; #[cfg(feature = "stream")] use pin_project_lite::pin_project; use crate::common::{ task::{self, Poll}, Pin, }; /// Asynchronously accept incoming connections. pub trait Accept { /// The connection type that can be accepted. type Conn; /// The error type that can occur when accepting a connection. type Error; /// Poll to accept the next connection. fn poll_accept( self: Pin<&mut Self>, cx: &mut task::Context<'_>, ) -> Poll>>; } /// Create an `Accept` with a polling function. /// /// # Example /// /// ``` /// use std::task::Poll; /// use hyper::server::{accept, Server}; /// /// # let mock_conn = (); /// // If we created some mocked connection... /// let mut conn = Some(mock_conn); /// /// // And accept just the mocked conn once... /// let once = accept::poll_fn(move |cx| { /// Poll::Ready(conn.take().map(Ok::<_, ()>)) /// }); /// /// let builder = Server::builder(once); /// ``` pub fn poll_fn(func: F) -> impl Accept where F: FnMut(&mut task::Context<'_>) -> Poll>>, { struct PollFn(F); // The closure `F` is never pinned impl Unpin for PollFn {} impl Accept for PollFn where F: FnMut(&mut task::Context<'_>) -> Poll>>, { type Conn = IO; type Error = E; fn poll_accept( self: Pin<&mut Self>, cx: &mut task::Context<'_>, ) -> Poll>> { (self.get_mut().0)(cx) } } PollFn(func) } /// Adapt a `Stream` of incoming connections into an `Accept`. /// /// # Optional /// /// This function requires enabling the `stream` feature in your /// `Cargo.toml`. #[cfg(feature = "stream")] pub fn from_stream(stream: S) -> impl Accept where S: Stream>, { pin_project! { struct FromStream { #[pin] stream: S, } } impl Accept for FromStream where S: Stream>, { type Conn = IO; type Error = E; fn poll_accept( self: Pin<&mut Self>, cx: &mut task::Context<'_>, ) -> Poll>> { self.project().stream.poll_next(cx) } } FromStream { stream } }