Help me to solve this build issue

I have this rust code

use std::collections::HashMap;
pub trait BarType {}
pub trait FooType {}
pub trait SuperError {}

pub trait MyTrait {
    type Foo: FooType;
    type Bar: BarType;
    type Error: SuperError;

    fn get_str(
        // &self,
        foo: &Self::Foo,
    ) -> Result<String, Self::Error>
    where
        Self: Sized;

    fn setup(foo: &Self::Foo) -> Result<Self, Self::Error>
    where
        Self: Sized;

    fn process(&mut self, bar: &Self::Bar) -> Result<(), Self::Error>;
}

#[derive(Debug)]
enum MyError {}

impl SuperError for MyError {}
struct Builder {
    pub data_source: HashMap<
        String,
        Box<dyn MyTrait<Foo = dyn BarType, Bar = dyn FooType, Error = dyn SuperError>>,
    >,
}

impl Builder {
    pub fn build(&self) -> Mystruct {
        Mystruct {}
    }
    pub fn new() -> Self {
        Self {
            data_source: HashMap::new(),
        }
    }
    pub fn fill_data_source(
        &mut self,
        name: &str,
        value: Box<dyn MyTrait<Foo = dyn BarType, Bar = dyn FooType, Error = dyn SuperError>>,
    ) {
        self.data_source.insert(name.to_string(), value);
    }
}

struct Mystruct {}

struct Baz {}
impl MyTrait for Baz {
    type Foo = i32;
    type Bar = i32;
    type Error = MyError;

    fn get_str(foo: &Self::Foo) -> Result<String, Self::Error>
    where
        Self: Sized,
    {
        Ok(String::new())
    }

    fn setup(foo: &Self::Foo) -> Result<Self, Self::Error>
    where
        Self: Sized,
    {
        Ok(Self {})
    }

    fn process(&mut self, bar: &Self::Bar) -> Result<(), Self::Error> {
        Ok(())
    }
}

impl Baz {
    fn new() -> Baz {
        Self {}
    }
}
impl<T> FooType for T {}
impl<T> BarType for T {}
fn main() {
    println!("Hello, world!");
    let mut b = Builder::new();
    let mut r = Baz::new();
    r.process(&100_i32).unwrap();
    b.fill_data_source("name", Box::new(Baz::new()));
    //let c = b.build();
}

which is giving me this error

error[E0271]: type mismatch resolving `<Baz as MyTrait>::Foo == (dyn BarType + 'static)`
  --> src/main.rs:93:32
   |
93 |     b.fill_data_source("name", Box::new(Baz::new()));
   |                                ^^^^^^^^^^^^^^^^^^^^ type mismatch resolving `<Baz as MyTrait>::Foo == (dyn BarType + 'static)`
   |
note: expected this to be `(dyn BarType + 'static)`
  --> src/main.rs:58:16
   |
58 |     type Foo = i32;
   |                ^^^
   = note: expected trait object `(dyn BarType + 'static)`
                      found type `i32`
   = note: required for the cast from `Baz` to the object type `dyn MyTrait<Foo = (dyn BarType + 'static), Bar = (dyn FooType + 'static), Error = (dyn SuperError + 'static)>`

error[E0271]: type mismatch resolving `<Baz as MyTrait>::Bar == (dyn FooType + 'static)`
  --> src/main.rs:93:32
   |
93 |     b.fill_data_source("name", Box::new(Baz::new()));
   |                                ^^^^^^^^^^^^^^^^^^^^ type mismatch resolving `<Baz as MyTrait>::Bar == (dyn FooType + 'static)`
   |
note: expected this to be `(dyn FooType + 'static)`
  --> src/main.rs:59:16
   |
59 |     type Bar = i32;
   |                ^^^
   = note: expected trait object `(dyn FooType + 'static)`
                      found type `i32`
   = note: required for the cast from `Baz` to the object type `dyn MyTrait<Foo = (dyn BarType + 'static), Bar = (dyn FooType + 'static), Error = (dyn SuperError + 'static)>`

error[E0271]: type mismatch resolving `<Baz as MyTrait>::Error == (dyn SuperError + 'static)`
  --> src/main.rs:93:32
   |
93 |     b.fill_data_source("name", Box::new(Baz::new()));
   |                                ^^^^^^^^^^^^^^^^^^^^ type mismatch resolving `<Baz as MyTrait>::Error == (dyn SuperError + 'static)`
   |
note: expected this to be `(dyn SuperError + 'static)`
  --> src/main.rs:60:18
   |
60 |     type Error = MyError;
   |                  ^^^^^^^
   = note: expected trait object `(dyn SuperError + 'static)`
                      found enum `MyError`
   = note: required for the cast from `Baz` to the object type `dyn MyTrait<Foo = (dyn BarType + 'static), Bar = (dyn FooType + 'static), Error = (dyn SuperError + 'static)>`

For more information about this error, try `rustc --explain E0271`.
error: could not compile `erased_trait` due to 3 previous errors

I dont understand this error. help me how i can get rid of this error

The problem is that an implementation of impl SomeTrait for SomeStruct { type Associated = Foo; } will only allow you to turn SomeStruct into dyn SomeTrait<Associated = Foo>, but not dyn SomeTrait<Associated = dyn OtherTraitImplementedByFoo>.

There are additional minor problems such as the fact that your associated types Foo/Bar/Error don’t even actively allow unsized types, and Error is used in a way where unsized types wouldn’t work in Result<_, Self::Error>.

There’s no good way to fix the problem either: A type like Baz implements MyTrait in a way that it expects the specific type i32 in the role of Foo as arguments to the functions get_str and setup. Wanting to use Baz in the rule of dyn MyTrait<Foo = dyn FooType, …> however suggests that an implementation of these functions must be present of that accepts _any FooType type, not just i32.

Perhaps your code doesn’t accurately represent what you’re actually trying to achieve here. As it’s a very foo-bar-baz style example, it’s impossible for me to guess whether you have any practical use-case that this code structure came up in (and if so, which kind of use case it is). So while what your code tells me you’re trying to achieve is impossible, maybe what you’re actually trying to achieve can be done, so feel free to give some more context!

This topic was automatically closed 90 days after the last reply. We invite you to open a new topic if you have further questions or comments.