"one type is more general than the other" chain of problems

I have made a few forum posts lately with the "one type is more general than the other" error and my apologies for making another one, but this one is just to present my entire problem to avoid the XY problem. Any attempt to solve one problem leads to another, and here they all are, completely reproducible. I guess it won't be solved any time soon as well, so better have it all in one place here.

I am working on s3-algo. This is the current master: Make sure all futures are Send + 'static · openanalytics/s3-algo@e4fba8a · GitHub cargo test succeeds. :+1:

However, it does not work with futures::executor::ThreadPool (due to Send + 'static bounds). Minimal complete example:
main.rs

use rusoto_s3::*;
use s3_algo::{files_recursive, s3_upload_files, UploadConfig};
use std::path::PathBuf;

fn main() {
    println!("Hello, world!");
}

pub fn spawn_copy_job() {
    let pool = futures::executor::ThreadPool::new().unwrap();
    pool.spawn_ok(async move {
        let uploads = s3_upload_files(
            s3_client(),
            String::new(),
            files_recursive(PathBuf::new(), PathBuf::new()),
            UploadConfig::default(),
            |_| (),
            s3_put_request_factory(false),
        )
        .await;
    })
}

pub fn s3_client() -> rusoto_s3::S3Client {
    unimplemented!()
}

pub fn s3_put_request_factory(dry_run: bool) -> impl Fn() -> PutObjectRequest + Clone + 'static {
    move || {
        unimplemented!();
    }
}

Cargo.toml

[package]
name = "minimal_more_general"
version = "0.1.0"
authors = ["Erlend Langseth <3rlendhl@gmail.com>"]
edition = "2018"

# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html

[dependencies]
futures = {version = "0.3.1", features = ["thread-pool"] }
rusoto_s3 = "0.43.0-beta.1"
s3-algo = "0.1.9"

Error

error[E0308]: mismatched types
  --> src/main.rs:11:10
   |
11 |     pool.spawn_ok(async move {
   |          ^^^^^^^^ one type is more general than the other
   |
   = note: expected type `std::ops::FnOnce<(std::pin::Pin<std::boxed::Box<dyn core::future::future::Future<Output = std::result::Result<(s3_algo::RequestReport, ()), s3_algo::err::Error>> + std::marker::Send>>,)>`
              found type `std::ops::FnOnce<(std::pin::Pin<std::boxed::Box<dyn core::future::future::Future<Output = std::result::Result<(s3_algo::RequestReport, ()), s3_algo::err::Error>> + std::marker::Send>>,)>`

error[E0308]: mismatched types
  --> src/main.rs:11:10
   |
11 |     pool.spawn_ok(async move {
   |          ^^^^^^^^ one type is more general than the other
   |
   = note: expected opaque type `impl core::future::future::Future`
              found opaque type `impl core::future::future::Future`

error: aborting due to 2 previous errors 

Removing the .boxed() inside the s3_upload_files function gets rid of that error (cargo check is successful), but I get "type length limit reached" error now cargo build --tests. To reproduce: remove .boxed() from latest s3-algo master and run cargo test (Make sure all futures are Send + 'static · openanalytics/s3-algo@e4fba8a · GitHub)

Replacing .boxed() with Box::pin should fix the problem, but I fail to do so too: How to put a future in Pin<Box<>> without .boxed()? (if I don't cast with as ..., I get the type length limit problem again)

And finally, if I remove this .then https://github.com/openanalytics/s3-algo/blob/e4fba8aa014913fccf00940585c74e81986f9d02/src/upload.rs#L61 it all works as well. But I have not found any other way to insert a delay there, including using StreamExt::map.

1 Like

This topic was automatically closed 90 days after the last reply. New replies are no longer allowed.