Recently procedural macros are getting much attention. One usage of such macros is custom derive, that allows defining macros that allow deriving trait implementations easily. (See https://github.com/rust-lang/rfcs/pull/1681)
There’s also a problem with traits: the trait coherence rules, which prevent crates from having incompatible trait implementations with each other, prevent also some useful patterns. Let’s say that I use the library Serde
for serialization. I also use some upstream crate Foo
of which I have no control over. I want to serialize struct Bar
from crate Foo
, but the author haven’t had the foresight to derive or implement the trait that allows this for the struct.
The coherence rules are there for a reason: if anybody could implement the serialization traits, there could be conflicting implementations introduced by third party libraries, and thus linking together some unfortunate combination of libraries could break the build.
I think we could remedy the situation by allowing the trait author to provide deriving macros for procedural blanket impls. The idea is that the impl
would be derived for any struct/enum without even the struct/enum authors opting in, unlike with the current derived impls. The struct/enum author could, however, provide their own impl that overrides the blanket impl, or opt out from derivations.
The derivation would happen at the downstream crate that imports and uses a combination of a trait and a struct/enum. I think that would help at least with the coherence problems with Serde
and some other crates that have algorithmically derivable impl
s.
I originally wrote about this idea in https://github.com/rust-lang/rfcs/issues/1553, but there wasn’t much discussion. What do you all think?