Files
reth/crates/engine/local/src/miner.rs
2024-09-20 03:50:42 +00:00

61 lines
1.8 KiB
Rust

//! Contains the implementation of the mining mode for the local engine.
use alloy_primitives::TxHash;
use futures_util::{stream::Fuse, StreamExt};
use reth_transaction_pool::TransactionPool;
use std::{
future::Future,
pin::Pin,
task::{Context, Poll},
time::Duration,
};
use tokio::time::Interval;
use tokio_stream::wrappers::ReceiverStream;
/// A mining mode for the local dev engine.
#[derive(Debug)]
pub enum MiningMode {
/// In this mode a block is built as soon as
/// a valid transaction reaches the pool.
Instant(Fuse<ReceiverStream<TxHash>>),
/// In this mode a block is built at a fixed interval.
Interval(Interval),
}
impl MiningMode {
/// Constructor for a [`MiningMode::Instant`]
pub fn instant<Pool: TransactionPool>(pool: Pool) -> Self {
let rx = pool.pending_transactions_listener();
Self::Instant(ReceiverStream::new(rx).fuse())
}
/// Constructor for a [`MiningMode::Interval`]
pub fn interval(duration: Duration) -> Self {
let start = tokio::time::Instant::now() + duration;
Self::Interval(tokio::time::interval_at(start, duration))
}
}
impl Future for MiningMode {
type Output = ();
fn poll(self: Pin<&mut Self>, cx: &mut Context<'_>) -> Poll<Self::Output> {
let this = self.get_mut();
match this {
Self::Instant(rx) => {
// drain all transactions notifications
if let Poll::Ready(Some(_)) = rx.poll_next_unpin(cx) {
return Poll::Ready(())
}
Poll::Pending
}
Self::Interval(interval) => {
if interval.poll_tick(cx).is_ready() {
return Poll::Ready(())
}
Poll::Pending
}
}
}
}