Why does generic type parameterized by "my type" violate orphan rule?

Let’s suppose that we have concrete type defined in one crate Lib1Foo
and generic type defined in another:

pub struct Lib2Boo<T> {
    x: T,
}

and in the third crate I want to write something like this:

struct MyType;
impl From<Lib1Foo> for Lib2Boo<MyType> {
    fn from(_: Lib1Foo) -> Self {
        unimplemented!();
    }
}

Why this is violation of

the impl does not reference only types defined in this crate
This error indicates a violation of one of Rust's orphan rules for trait
implementations

?

MyType defined in the current crate,
so Lib2Boo<MyType> technically is local crate type,
because of MyType is defined in current crate, no?

MyType defined in the current crate,
so Lib2Boo<MyType> technically is local crate type,
because of MyType is defined in current crate, no?

Nop, the “root” (Lib2Boo) is what matters.

This impl is forbidden so that Lib2 is permitted to add something like the following in a minor semver bump:

impl<T> From<Lib1Foo> for Lib2Boo<T> {
    fn from(_: Lib1Foo) -> Self { ... }
}

Note there is an accepted RFC to weaken the orphan rules, but it won’t enable this case.

4 Likes