Reputation: 175
I have created a generic trait, and I am implementing it in a sqlx query, but I get an error
what am I doing wrong?
#[async_trait]
pub trait ITodoRepo<P> {
async fn list(pool:&P) -> Result<Vec<TodoType>>;
}
pub struct TodoRepo;
#[async_trait]
impl<P: sqlx::Executor<'static, Database = sqlx::Postgres>> ITodoRepo<P> for TodoRepo {
async fn list(pool: &P) -> Result<Vec<TodoType>> {
let rowset = sqlx::query_as!(
TodoSchema,
r#"SELECT * FROM todo"#)
.fetch_all(pool)
.await?
.iter()
.map(|row| hydrate(row))
.collect();
Ok(rowset)
}
}
How can I implement the Executor?
error[E0637]: `'_` cannot be used here
--> src/todo.rs:21:24
|
21 | .fetch_all(pool)
| ^^^^ the trait `sqlx::Executor<'_>` is not implemented for `&P`
Upvotes: 1
Views: 1040
Reputation: 6779
In you question, as per fn list(pool: &P)
, the type of pool
is &P
. But the fetch_all()
method seems to require an argument that implement trait sqlx::Executor<'_>
. P
implements that trait as per your impl but &P
doesn't.
Here is a minimal reproducible code for your question:
trait MyTrait {}
struct MyStruct;
impl MyTrait for MyStruct {}
fn func<T: MyTrait>(arg: T) {
todo!()
}
fn main() {
let var = MyStruct;
let ref_to_var = &var;
func(ref_to_var);
}
Basically your function is expecting a type T
that implements some trait MyTrait
but you are passing &T
.
To fix this, you can either change to function to accept a reference. Like in the above example:
fn func<T: MyTrait>(arg: &T) {
todo!()
}
Or you could implement the trait for the reference itself:
impl MyTrait for &MyStruct {}
Upvotes: 2