pub trait Foo {}
pub struct MyFoo {}
impl Foo for MyFoo {}
trait Bar<T> where T: Foo {
fn do_something(&self, my_foo: T) -> Result<T, str>;
}
pub struct MyBar {}
impl Bar<MyFoo> for MyBar {
fn do_something(&self, my_foo: MyFoo) -> Result<(), str> {
// MyBar implementation
Ok(())
}
}
pub struct YourBar {}
impl Bar<MyFoo> for YourBar {
fn do_something(&self, my_foo: MyFoo) -> Result<(), str> {
// YourBar implementation
Ok(())
}
}
fn test() {
let arc_foo : Arc<dyn Bar<MyFoo> + Send + Sync> = wrapper.get_bar();
let actix_data = Data::new(arc_foo.clone());
// pass actix_data to the function expecting it
// then call actix_data.do_something() that should execute the implementation of the current Bar (MyBar or YourBar)
}
I would like to extract the Bar variable to assemble an Actix-web Application state of type web::Data<T> where T: Bar<MyFoo>, something like Data::new(arc_foo.clone())
I'm trying several solution but I'm not able to pass from one to another. I know that the Arc does contain a type that also implement Send and Sync, but I need them for other reasons. Is there a way to convert the first variable to the second one?
Thanks quinedot,
however I've simplified my real code to ease it. With your solution I need to implement all the functions declared by the Bar trait but I would like to avoid this approach because my real implementations are within MyBar and YourBar and I would use those ones.
Or is there a way to bind them?
Your implementations don't match the trait declaration (and str is not Sized). But this maybe? the only real relevant addition is calling the dyn Bar<U> from &Arc<dyn ...>.
This solution is working, even if I had to tweak a bit to adhere to my real implementation where I have aysnc traits so some Send + Sync were required to make it working. Moreover, as suggested by @moy2010 I had to add the static bound besides Send and Sync to be able to pass to the actix Data.
So for the others, starting with: