Trait IntoFuture

1.64.0 ยท Source
pub trait IntoFuture {
    type Output;
    type IntoFuture: Future<Output = Self::Output>;

    // Required method
    fn into_future(self) -> Self::IntoFuture;
}
Expand description

Conversion into a Future.

By implementing IntoFuture for a type, you define how it will be converted to a future.

ยง.await desugaring

The .await keyword desugars into a call to IntoFuture::into_future first before polling the future to completion. IntoFuture is implemented for all T: Future which means the into_future method will be available on all futures.

use std::future::IntoFuture;

let v = async { "meow" };
let mut fut = v.into_future();
assert_eq!("meow", fut.await);

ยงAsync builders

When implementing futures manually there will often be a choice between implementing Future or IntoFuture for a type. Implementing Future is a good choice in most cases. But implementing IntoFuture is most useful when implementing โ€œasync builderโ€ types, which allow their values to be modified multiple times before being .awaited.

use std::future::{ready, Ready, IntoFuture};

/// Eventually multiply two numbers
pub struct Multiply {
    num: u16,
    factor: u16,
}

impl Multiply {
    /// Constructs a new instance of `Multiply`.
    pub fn new(num: u16, factor: u16) -> Self {
        Self { num, factor }
    }

    /// Set the number to multiply by the factor.
    pub fn number(mut self, num: u16) -> Self {
        self.num = num;
        self
    }

    /// Set the factor to multiply the number with.
    pub fn factor(mut self, factor: u16) -> Self {
        self.factor = factor;
        self
    }
}

impl IntoFuture for Multiply {
    type Output = u16;
    type IntoFuture = Ready<Self::Output>;

    fn into_future(self) -> Self::IntoFuture {
        ready(self.num * self.factor)
    }
}

// NOTE: Rust does not yet have an `async fn main` function, that functionality
// currently only exists in the ecosystem.
async fn run() {
    let num = Multiply::new(0, 0)  // initialize the builder to number: 0, factor: 0
        .number(2)                 // change the number to 2
        .factor(2)                 // change the factor to 2
        .await;                    // convert to future and .await

    assert_eq!(num, 4);
}

ยงUsage in trait bounds

Using IntoFuture in trait bounds allows a function to be generic over both Future and IntoFuture. This is convenient for users of the function, so when they are using it they donโ€™t have to make an extra call to IntoFuture::into_future to obtain an instance of Future:

use std::future::IntoFuture;

/// Converts the output of a future to a string.
async fn fut_to_string<Fut>(fut: Fut) -> String
where
    Fut: IntoFuture,
    Fut::Output: std::fmt::Debug,
{
    format!("{:?}", fut.await)
}

Required Associated Typesยง

1.64.0 ยท Source

type Output

The output that the future will produce on completion.

1.64.0 ยท Source

type IntoFuture: Future<Output = Self::Output>

Which kind of future are we turning this into?

Required Methodsยง

1.64.0 ยท Source

fn into_future(self) -> Self::IntoFuture

Creates a future from a value.

ยงExamples

Basic usage:

use std::future::IntoFuture;

let v = async { "meow" };
let mut fut = v.into_future();
assert_eq!("meow", fut.await);

Implementorsยง

ยง

impl<'a, T, F> IntoFuture for &'a Lazy<T, F>
where F: Future<Output = T> + Unpin,

ยง

type Output = &'a T

ยง

type IntoFuture = LazyFutureUnpin<'a, T, F>

ยง

impl<'a, T, F> IntoFuture for Pin<&'a Lazy<T, F>>
where F: Future<Output = T>,

ยง

type Output = Pin<&'a T>

ยง

type IntoFuture = LazyFuturePin<'a, T, F>

1.64.0 ยท Sourceยง

impl<F> IntoFuture for F
where F: Future,

ยง

impl<L, M, S> IntoFuture for Serve<L, M, S>
where <L as Listener>::Addr: Debug, M: for<'a> Service<IncomingStream<'a, L>, Error = Infallible, Response = S> + Send + 'static, <M as Service<IncomingStream<'a, L>>>::Future: for<'a> Send, S: Service<Request<Body>, Response = Response<Body>, Error = Infallible> + Clone + Send + 'static, L: Listener, <S as Service<Request<Body>>>::Future: Send,

ยง

type Output = Result<(), Error>

ยง

type IntoFuture = ServeFuture

ยง

impl<L, M, S, F> IntoFuture for WithGracefulShutdown<L, M, S, F>
where <L as Listener>::Addr: Debug, M: for<'a> Service<IncomingStream<'a, L>, Error = Infallible, Response = S> + Send + 'static, <M as Service<IncomingStream<'a, L>>>::Future: for<'a> Send, S: Service<Request<Body>, Response = Response<Body>, Error = Infallible> + Clone + Send + 'static, <S as Service<Request<Body>>>::Future: Send, F: Future<Output = ()> + Send + 'static, L: Listener,

ยง

type Output = Result<(), Error>

ยง

type IntoFuture = ServeFuture

ยง

impl<T> IntoFuture for ArcAsyncDerived<T>
where T: Clone + 'static,

ยง

impl<T> IntoFuture for ArcLocalResource<T>
where T: Clone + 'static,

ยง

impl<T> IntoFuture for LocalResource<T>
where T: Clone + 'static,

ยง

impl<T, S> IntoFuture for AsyncDerived<T, S>
where T: Clone + 'static, S: Storage<ArcAsyncDerived<T>>,

ยง

impl<T, Ser> IntoFuture for ArcOnceResource<T, Ser>
where T: Clone + 'static,

ยง

impl<T, Ser> IntoFuture for ArcResource<T, Ser>
where T: Clone + 'static,

ยง

impl<T, Ser> IntoFuture for OnceResource<T, Ser>
where T: Clone + Send + Sync + 'static, Ser: 'static,

ยง

impl<T, Ser> IntoFuture for Resource<T, Ser>
where T: Clone + Send + Sync + 'static,