Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add TcpListener::into_incoming and IntoIncoming #88339

Merged
merged 1 commit into from
Sep 17, 2021
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
51 changes: 51 additions & 0 deletions library/std/src/net/tcp.rs
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,18 @@ pub struct Incoming<'a> {
listener: &'a TcpListener,
}

/// An iterator that infinitely [`accept`]s connections on a [`TcpListener`].
///
/// This `struct` is created by the [`TcpListener::into_incoming`] method.
/// See its documentation for more.
///
/// [`accept`]: TcpListener::accept
#[derive(Debug)]
#[unstable(feature = "tcplistener_into_incoming", issue = "88339")]
pub struct IntoIncoming {
listener: TcpListener,
}

impl TcpStream {
/// Opens a TCP connection to a remote host.
///
Expand Down Expand Up @@ -798,6 +810,37 @@ impl TcpListener {
Incoming { listener: self }
}

/// Turn this into an iterator over the connections being received on this
/// listener.
///
/// The returned iterator will never return [`None`] and will also not yield
/// the peer's [`SocketAddr`] structure. Iterating over it is equivalent to
/// calling [`TcpListener::accept`] in a loop.
///
/// # Examples
///
/// ```no_run
/// #![feature(tcplistener_into_incoming)]
/// use std::net::{TcpListener, TcpStream};
///
/// fn listen_on(port: u16) -> impl Iterator<Item = TcpStream> {
/// let listener = TcpListener::bind("127.0.0.1:80").unwrap();
/// listener.into_incoming()
/// .filter_map(Result::ok) /* Ignore failed connections */
/// }
///
/// fn main() -> std::io::Result<()> {
/// for stream in listen_on(80) {
/// /* handle the connection here */
/// }
/// Ok(())
/// }
/// ```
#[unstable(feature = "tcplistener_into_incoming", issue = "88339")]
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The tracking issue number here refers to this PR itself. Did something go wrong? Is there an actual tracking issue for this feature?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The tracking issue is #88373, so this likely was a mistake

pub fn into_incoming(self) -> IntoIncoming {
IntoIncoming { listener: self }
}

/// Sets the value for the `IP_TTL` option on this socket.
///
/// This value sets the time-to-live field that is used in every packet sent
Expand Down Expand Up @@ -935,6 +978,14 @@ impl<'a> Iterator for Incoming<'a> {
}
}

#[unstable(feature = "tcplistener_into_incoming", issue = "88339")]
impl Iterator for IntoIncoming {
type Item = io::Result<TcpStream>;
fn next(&mut self) -> Option<io::Result<TcpStream>> {
Some(self.listener.accept().map(|p| p.0))
}
}

impl AsInner<net_imp::TcpListener> for TcpListener {
fn as_inner(&self) -> &net_imp::TcpListener {
&self.0
Expand Down