backon
backon copied to clipboard
Use with sqlx?
Hey!
The library seems pretty cool! I am new to rust, trying to implement a retry strategy on a small rest API project. Could you help me understand how to use it?
I am trying to implement a retry strategy on a SQLx query. If it fails I want to retry it before returning a 5xx error.
I would normally run the code such as:
query
.execute(pool.inner())
.await
Now, with backon; This doesn't work -
query
.execute(pool.inner())
.retry(&ExponentialBuilder::default())
.await
Error:
| error[E0599]: the method `retry` exists for opaque type `impl Future<Output = Result<<Postgres as Database>::QueryResult, Error>>`, but its trait bounds were not satisfied
| --> src/model/user/create.rs:105:10
| |
| 103 | let rows_affected = query
| | _________________________-
| 104 | | .execute(pool.inner())
| 105 | | .retry(&ExponentialBuilder::default())
| | | -^^^^^ method cannot be called due to unsatisfied trait bounds
| | |_________|
| |
| |
| = note: the following trait bounds were not satisfied:
| `<impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>> as FnOnce<(_,)>>::Output = _`
| which is required by `impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: RetryableWithContext<_, _, _, _, _, impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>>`
| `impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: FnMut<(_,)>`
| which is required by `impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: RetryableWithContext<_, _, _, _, _, impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>>`
| `<&impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>> as FnOnce<(_,)>>::Output = _`
| which is required by `&impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: RetryableWithContext<_, _, _, _, _, &impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>>`
| `&impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: FnMut<(_,)>`
| which is required by `&impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: RetryableWithContext<_, _, _, _, _, &impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>>`
| `<&mut impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>> as FnOnce<(_,)>>::Output = _`
| which is required by `&mut impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: RetryableWithContext<_, _, _, _, _, &mut impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>>`
| `&mut impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: FnMut<(_,)>`
| which is required by `&mut impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>: RetryableWithContext<_, _, _, _, _, &mut impl std::future::Future<Output = Result<<Postgres as sqlx::Database>::QueryResult, sqlx::Error>>>`
And using a lamba doesn't seem to work either:
{
|| async {
let connection = pool.acquire().await.map_err(anyhow::Error::from)?;
query.execute(connection).await.map_err(anyhow::Error::from)
}
}
.retry(&ExponentialBuilder::default())
.await?;
Error:
| error[E0277]: the trait bound `sqlx::pool::PoolConnection<Postgres>: Executor<'_>` is not satisfied
| --> src/model/user/create.rs:105:27
| |
| 105 | query.execute(connection).await.map_err(anyhow::Error::from)
| | ------- ^^^^^^^^^^ the trait `Executor<'_>` is not implemented for `sqlx::pool::PoolConnection<Postgres>`
| | |
| | required by a bound introduced by this call
| |
| = help: the following other types implement trait `Executor<'c>`:
| <&'c mut PgConnection as Executor<'c>>
| <&'c mut PgListener as Executor<'c>>
| <&'c mut AnyConnection as Executor<'c>>
| <&Pool<DB> as Executor<'p>>
| note: required by a bound in `sqlx::query::Query::<'q, DB, A>::execute`
| --> /usr/local/cargo/registry/src/index.crates.io-6f17d22bba15001f/sqlx-core-0.7.4/src/query.rs:155:12
| |
| 151 | pub async fn execute<'e, 'c: 'e, E>(self, executor: E) -> Result<DB::QueryResult, Error>
| | ------- required by a bound in this associated function
| ...
| 155 | E: Executor<'c, Database = DB>,
| | ^^^^^^^^^^^^^^^^^^^^^^^^^^^ required by this bound in `Query::<'q, DB, A>::execute`