Enum_dispatch with trait & enum defined in different crates?

Hello, I have been splitting my project into multiple distinct crates in order to improve compile times. I'm trying to do a "data types" crate with my general data structures for serialization and a "business logic" crate that processes that data. One problem I'm running into is that I currently use the enum_dispatch crate to automatically implement traits:

#[enum_dispatch]
trait KnobControl {
    //...
}

#[enum_dispatch(KnobControl)]
enum Knob {
    LinearKnob,
    LogarithmicKnob,
}

This presents a natural problem because the Knob enum now needs to live in the "data types" crate (it's embedded within numerous other important datatypes and participates in serialization) but the KnobControl trait needs to live in the "business logic" crate (the implementations of the trait functions call into other primary business logic functions).

So what I really need is a macro which generates an implementation of the KnobControl trait in a different crate from the crate where the Knob enum lives. Is there an alternative crate to enum_dispatch which accomplishes this goal?

I don't have an answer for that, just some more general thoughts that may or may not apply (please just ignore this if they don't.)

Is KnobControl only implemented by Knob, or by other types? If only Knob, then they probably belong together in the same crate, irrespective of the problem with enum_dispatch.

One thing discouraged in Rust is to put data types into a separate module, much less a separate crate. So modules/crates would normally be separated by functionality. That's just a recommended organization that comes from the desire to see the types and the code that uses them together. In other languages there are sometimes patterns where types are separated, but not so much in Rust.

Putting data types in a separate crate could also make it more likely to have problems with the orphan rule: crate X cannot implement a trait in crate Y for a type in crate Z, nor can X implement a trait in Y for a type in Y. If X implements a trait, it must also contain either the type or the trait.

1 Like

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.