1

In Rust, I am trying to create an object of type Installer and pass a DownloaderFoo or DownloaderBar to its constructor (playground):

pub trait Downloader {
    fn run(&self);
}

pub struct DownloaderFoo;
impl Downloader for DownloaderFoo {
    fn run(&self)  {
        println!("DownloaderFoo::run");
    }
}

pub struct DownloaderBar;
impl Downloader for DownloaderBar {
    fn run(&self)  {
        println!("DownloaderBar::run");
    }
}

pub struct Installer {
    downloader: Downloader,
}

impl Installer {
    pub fn run(&self) {
        self.downloader.run();
        println!("Installer::run");
    }
}

fn main() {
    Installer{downloader: DownloaderFoo{}}.run();
    Installer{downloader: DownloaderBar{}}.run();
}

I get the following compile error:

   Compiling playground v0.0.1 (/playground)
warning: trait objects without an explicit `dyn` are deprecated
  --> src/main.rs:20:17
   |
20 |     downloader: Downloader,
   |                 ^^^^^^^^^^ help: use `dyn`: `dyn Downloader`
   |
   = note: `#[warn(bare_trait_objects)]` on by default

error[E0308]: mismatched types
  --> src/main.rs:30:27
   |
30 |     Installer{downloader: DownloaderFoo{}}.run();
   |                           ^^^^^^^^^^^^^^^ expected trait object `dyn Downloader`, found struct `DownloaderFoo`
   |
   = note: expected trait object `(dyn Downloader + 'static)`
                    found struct `DownloaderFoo`

I tried using dyn Downloader in the Installer members, but I'm a bit stuck and don't know how to move forward.

Any ideas here? Thank you!

Mihai Galos
  • 1,707
  • 1
  • 19
  • 38

1 Answers1

3

The issue is that dyn Downloader does not have a size known at compile time. You can fix this by wrapping it in a Box, which is pointer to an object on the heap:

pub struct Installer {
    downloader: Box<dyn Downloader>,
}

And inject the Downloaders like so:

fn main() {
    Installer{downloader: Box::new(DownloaderFoo{})}.run();
    Installer{downloader: Box::new(DownloaderBar{})}.run();
}

For more information about the Sized trait, see What does “Sized is not implemented” mean?

Ibraheem Ahmed
  • 11,652
  • 2
  • 48
  • 54