I've recently encountered this rather hard to read lifetime error:
error[E0623]: lifetime mismatch
--> src/lib.rs:50:28
|
43 | fn foo<'a, B>(&self, ay: &Ay<'a>, bs: &[B])
| -------
| |
| these two types are declared with different lifetimes...
...
50 | right: Cow::Owned(ThisBee { data: Cow::Borrowed(&ay.data) }),
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ ...but data from `ay` flows into `ay` here
error: aborting due to previous error
As you can see, the two types that are declared with different lifetimes are in fact the same type!
Here's a playground gist with a minimal example:
The error itself is easy enough to fix by changing Cow::Borrowed(&ay.data) to just ay.data.clone(), but I'm curious as to why the error message looks like that.
the lifetime of &ay.data is derived from &'2 Ay<'a>, so the type of Cow::Borrowed(&ay.data) is Cow<'2, Data>, notCow<'a, Data> (which is what it needs to be to type check against ThisBee<'a>). This is why the error message says data from `ay` flows into `ay` here: it's trying to tell you that data from a reference of lifetime '2 can flow into a reference of lifetime 'a, which would be bad.
The message is meant to point you in the right direction when you do something like this. But since both lifetimes are attached to the same argument in your example, the error message comes out kind of weird.
Besides cloning the Cow, another way to fix this in the example is to change the type annotation on TwoBees to <'_, '_, B, ThisBee<'_>> and let the compiler figure out that '_ is shorter than the 'a on foo.