feature: pending transaction retries repeatedly before assuming dropped (#1221)
This commit is contained in:
parent
bc958792af
commit
c70cd81de0
|
@ -153,6 +153,8 @@
|
||||||
|
|
||||||
### Unreleased
|
### Unreleased
|
||||||
|
|
||||||
|
- Add retries to the pending transaction future
|
||||||
|
[1221](https://github.com/gakonst/ethers-rs/pull/1221)
|
||||||
- Add support for basic and bearer authentication in http and non-wasm websockets.
|
- Add support for basic and bearer authentication in http and non-wasm websockets.
|
||||||
[829](https://github.com/gakonst/ethers-rs/pull/829)
|
[829](https://github.com/gakonst/ethers-rs/pull/829)
|
||||||
- Export `ethers_providers::IpcError` and `ethers_providers::QuorumError`
|
- Export `ethers_providers::IpcError` and `ethers_providers::QuorumError`
|
||||||
|
|
|
@ -62,8 +62,11 @@ pub struct PendingTransaction<'a, P> {
|
||||||
provider: &'a Provider<P>,
|
provider: &'a Provider<P>,
|
||||||
state: PendingTxState<'a>,
|
state: PendingTxState<'a>,
|
||||||
interval: Box<dyn Stream<Item = ()> + Send + Unpin>,
|
interval: Box<dyn Stream<Item = ()> + Send + Unpin>,
|
||||||
|
retries_remaining: usize,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const DEFAULT_RETRIES: usize = 3;
|
||||||
|
|
||||||
impl<'a, P: JsonRpcClient> PendingTransaction<'a, P> {
|
impl<'a, P: JsonRpcClient> PendingTransaction<'a, P> {
|
||||||
/// Creates a new pending transaction poller from a hash and a provider
|
/// Creates a new pending transaction poller from a hash and a provider
|
||||||
pub fn new(tx_hash: TxHash, provider: &'a Provider<P>) -> Self {
|
pub fn new(tx_hash: TxHash, provider: &'a Provider<P>) -> Self {
|
||||||
|
@ -74,6 +77,7 @@ impl<'a, P: JsonRpcClient> PendingTransaction<'a, P> {
|
||||||
provider,
|
provider,
|
||||||
state: PendingTxState::InitialDelay(delay),
|
state: PendingTxState::InitialDelay(delay),
|
||||||
interval: Box::new(interval(DEFAULT_POLL_INTERVAL)),
|
interval: Box::new(interval(DEFAULT_POLL_INTERVAL)),
|
||||||
|
retries_remaining: DEFAULT_RETRIES,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -111,6 +115,13 @@ impl<'a, P: JsonRpcClient> PendingTransaction<'a, P> {
|
||||||
|
|
||||||
self
|
self
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Set retries
|
||||||
|
#[must_use]
|
||||||
|
pub fn retries(mut self, retries: usize) -> Self {
|
||||||
|
self.retries_remaining = retries;
|
||||||
|
self
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'a, P> PendingTransaction<'a, P> {
|
impl<'a, P> PendingTransaction<'a, P> {
|
||||||
|
@ -188,11 +199,16 @@ impl<'a, P: JsonRpcClient> Future for PendingTransaction<'a, P> {
|
||||||
let tx_opt = tx_res.unwrap();
|
let tx_opt = tx_res.unwrap();
|
||||||
// If the tx is no longer in the mempool, return Ok(None)
|
// If the tx is no longer in the mempool, return Ok(None)
|
||||||
if tx_opt.is_none() {
|
if tx_opt.is_none() {
|
||||||
|
if *this.retries_remaining == 0 {
|
||||||
tracing::debug!("Dropped from mempool, pending tx {:?}", *this.tx_hash);
|
tracing::debug!("Dropped from mempool, pending tx {:?}", *this.tx_hash);
|
||||||
*this.state = PendingTxState::Completed;
|
*this.state = PendingTxState::Completed;
|
||||||
return Poll::Ready(Ok(None))
|
return Poll::Ready(Ok(None))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
*this.retries_remaining -= 1;
|
||||||
|
rewake_with_new_state!(ctx, this, PendingTxState::PausedGettingTx);
|
||||||
|
}
|
||||||
|
|
||||||
// If it hasn't confirmed yet, poll again later
|
// If it hasn't confirmed yet, poll again later
|
||||||
let tx = tx_opt.unwrap();
|
let tx = tx_opt.unwrap();
|
||||||
rewake_with_new_state_if!(
|
rewake_with_new_state_if!(
|
||||||
|
|
Loading…
Reference in New Issue