Skip to content

try_flatten_stream() in futures-preview 0.3.0 #1444

@ebkalderon

Description

@ebkalderon

With futures 0.1, it was possible to have a Future that resolves to a Stream and use flatten_stream() to get access to the underlying stream, but if the Future resulted in an Error, the resulting stream would short-circuit and resolve to an Error as well.

When working with futures-preview 0.3.0, handling this situation is pretty cumbersome:

let future = async {
    let response = await!(client.get(uri))?;
    Ok(response.into_body())
};

// Worse
let stream = future
    .then(|result| match result {
        Ok(stream) => future::ready(Box::pin(stream) as Pin<Box<dyn Stream<Item = _> + Send>>),
        Err(err) => future::ready(Box::pin(stream::once(future::err(err))) as Pin<Box<dyn Stream<Item = _> + Send>>),
    }).flatten_stream();

// Slightly better
let stream = future
    .map_ok(|stream| Box::pin(stream) as Pin<Box<dyn Stream<Item = _> + Send>>)
    .unwrap_or_else(|err| Box::pin(stream::once(future::err(err))))
    .flatten_stream();

It would be nice if there was a TryFutureExt::try_flatten_stream() method which could simplify the code above like so:

let future = async {
    let response = await!(client.get(uri))?;
    Ok(response.into_body())
};

let stream = future.try_flatten_stream();

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions