Description
I was trying to implement FromSql of rusqlite
for my reference type (with lifetime). And I faced an unclear error message, later I was explained that the trait does not allow the return type to borrow from the value argument since it doesn't specify lifetime parameter explicitly.
However, I thought that it worth filing a bug report about unhelpful error message anyway.
Here is a simplified code:
use std::error::Error;
use std::fmt;
#[derive(Copy, Clone, Debug, PartialEq)]
pub enum ValueRef<'a> {
Null,
Integer(i64),
Real(f64),
Text(&'a [u8]),
Blob(&'a [u8]),
}
impl<'a> ValueRef<'a> {
pub fn as_str(&self) -> FromSqlResult<&'a str> {
match *self {
ValueRef::Text(t) => {
std::str::from_utf8(t).map_err(|_| FromSqlError::InvalidType)
}
_ => Err(FromSqlError::InvalidType),
}
}
}
#[derive(Debug)]
#[non_exhaustive]
pub enum FromSqlError {
InvalidType
}
impl fmt::Display for FromSqlError {
fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
write!(f, "InvalidType")
}
}
impl Error for FromSqlError {}
pub type FromSqlResult<T> = Result<T, FromSqlError>;
pub trait FromSql: Sized {
fn column_result(value: ValueRef<'_>) -> FromSqlResult<Self>;
}
impl FromSql for &str {
fn column_result(value: ValueRef<'_>) -> FromSqlResult<&str> {
value.as_str()
}
}
pub fn main() {
println!("{}", "Hello World");
}
The error message I'm getting is:
error: `impl` item signature doesn't match `trait` item signature
--> src/main.rs:45:5
|
41 | fn column_result(value: ValueRef<'_>) -> FromSqlResult<Self>;
| ------------------------------------------------------------- expected fn(ValueRef<'_>) -> std::result::Result<&str, FromSqlError>
...
45 | fn column_result(value: ValueRef<'_>) -> FromSqlResult<&str> {
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ found fn(ValueRef<'_>) -> std::result::Result<&str, FromSqlError>
|
= note: expected `fn(ValueRef<'_>) -> std::result::Result<&str, FromSqlError>`
found `fn(ValueRef<'_>) -> std::result::Result<&str, FromSqlError>`
error: aborting due to previous error
error: could not compile `playground`.
To learn more, run the command again with --verbose.
So basically it says that I have a wrong signature, even though the expected and found signatures are the same.
I'm not sure what would be the right error message to raise here since I don't know lifetime rules quite well.
Here is, just in case, a link to playground
The rust version I'm using is: 1.44.0-nightly
, but it also reproduces on 1.43.1
.