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

Non-send future produced by chaining Stream combinators #2845

Closed
George-Miao opened this issue Mar 20, 2024 · 1 comment
Closed

Non-send future produced by chaining Stream combinators #2845

George-Miao opened this issue Mar 20, 2024 · 1 comment

Comments

@George-Miao
Copy link

The future produced by chaining filter_map and chunks with a self reference inside filter_map closure is not Send for some reason, and this can be fixed by adding a .boxed() after the chunks call.

fn assert_send<T: Send>(t: T) -> T { t }
async fn test() {
    struct A;
    impl A {
        async fn a(&self) {
            futures::stream::iter([0u8])
                .filter_map(|_| async {
                    self.c();
                    // self.b().await; // Same as calling `c`
                    Some(0)
                })
                .chunks(1)
                // .boxed() // This will fix the problem
                .for_each(|_| async {}) // This can be anything consumes the stream without pinning it, include for_each_concurrent and collect
                .await;
        }

        async fn b(&self) {}

        fn c(&self) {}
    }
    assert_send(A.a()).await; // This will fail to compile
}

Error:

error[E0308]: mismatched types
   --> [:REDACTED:]/test.rs:252:9
    |
231 |                       .filter_map(|_| async {
    |  _____________________________________-
232 | |                         self.c();
233 | |                         // self.b().await; // Same as calling `c`
234 | |                         Some(0)
235 | |                     })
    | |                     -
    | |                     |
    | |_____________________the expected `async` block
    |                       the found `async` block
...
252 |           assert_send(A.a_consume()).await; // This will fail to compile
    |           ^^^^^^^^^^^^^^^^^^^^^^^^^^ one type is more general than the other
    |
    = note: expected `async` block `{async block@[:REDACTED:]/test.rs:231:37: 235:22}`
               found `async` block `{async block@[:REDACTED:]/test.rs:231:37: 235:22}`
note: the lifetime requirement is introduced here
   --> [:REDACTED:]/test.rs:223:23
    |
223 |     fn assert_send<T: Send>(t: T) -> T {
    |                       ^^^^

For more information about this error, try `rustc --explain E0308`.
@taiki-e
Copy link
Member

taiki-e commented Mar 20, 2024

This is a rustc bug: rust-lang/rust#104382

Closing in favor of the upstream issue.

@taiki-e taiki-e closed this as completed Mar 20, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants