mirror of
https://github.com/paradigmxyz/reth.git
synced 2026-02-19 03:04:27 -05:00
perf(prune): use bulk table clear for PruneMode::Full (#21302)
This commit is contained in:
committed by
GitHub
parent
4b1c341ced
commit
f692ac7d1e
@@ -9,6 +9,16 @@ use std::{fmt::Debug, ops::RangeBounds};
|
||||
use tracing::debug;
|
||||
|
||||
pub(crate) trait DbTxPruneExt: DbTxMut + DbTx {
|
||||
/// Clear the entire table in a single operation.
|
||||
///
|
||||
/// This is much faster than iterating entry-by-entry for `PruneMode::Full`.
|
||||
/// Returns the number of entries that were in the table.
|
||||
fn clear_table<T: Table>(&self) -> Result<usize, DatabaseError> {
|
||||
let count = self.entries::<T>()?;
|
||||
<Self as DbTxMut>::clear::<T>(self)?;
|
||||
Ok(count)
|
||||
}
|
||||
|
||||
/// Prune the table for the specified pre-sorted key iterator.
|
||||
///
|
||||
/// Returns number of rows pruned.
|
||||
|
||||
@@ -6,7 +6,7 @@ use crate::{
|
||||
use reth_db_api::{tables, transaction::DbTxMut};
|
||||
use reth_provider::{BlockReader, DBProvider, TransactionsProvider};
|
||||
use reth_prune_types::{
|
||||
PruneMode, PrunePurpose, PruneSegment, SegmentOutput, SegmentOutputCheckpoint,
|
||||
PruneMode, PruneProgress, PrunePurpose, PruneSegment, SegmentOutput, SegmentOutputCheckpoint,
|
||||
};
|
||||
use tracing::{instrument, trace};
|
||||
|
||||
@@ -48,6 +48,25 @@ where
|
||||
};
|
||||
let tx_range_end = *tx_range.end();
|
||||
|
||||
// For PruneMode::Full, clear the entire table in one operation
|
||||
if self.mode.is_full() {
|
||||
let pruned = provider.tx_ref().clear_table::<tables::TransactionSenders>()?;
|
||||
trace!(target: "pruner", %pruned, "Cleared transaction senders table");
|
||||
|
||||
let last_pruned_block = provider
|
||||
.block_by_transaction_id(tx_range_end)?
|
||||
.ok_or(PrunerError::InconsistentData("Block for transaction is not found"))?;
|
||||
|
||||
return Ok(SegmentOutput {
|
||||
progress: PruneProgress::Finished,
|
||||
pruned,
|
||||
checkpoint: Some(SegmentOutputCheckpoint {
|
||||
block_number: Some(last_pruned_block),
|
||||
tx_number: Some(tx_range_end),
|
||||
}),
|
||||
});
|
||||
}
|
||||
|
||||
let mut limiter = input.limiter;
|
||||
|
||||
let mut last_pruned_transaction = tx_range_end;
|
||||
|
||||
@@ -8,7 +8,7 @@ use rayon::prelude::*;
|
||||
use reth_db_api::{tables, transaction::DbTxMut};
|
||||
use reth_provider::{BlockReader, DBProvider, PruneCheckpointReader, StaticFileProviderFactory};
|
||||
use reth_prune_types::{
|
||||
PruneCheckpoint, PruneMode, PrunePurpose, PruneSegment, SegmentOutputCheckpoint,
|
||||
PruneCheckpoint, PruneMode, PruneProgress, PrunePurpose, PruneSegment, SegmentOutputCheckpoint,
|
||||
};
|
||||
use reth_static_file_types::StaticFileSegment;
|
||||
use tracing::{debug, instrument, trace};
|
||||
@@ -82,6 +82,26 @@ where
|
||||
}
|
||||
}
|
||||
.into_inner();
|
||||
|
||||
// For PruneMode::Full, clear the entire table in one operation
|
||||
if self.mode.is_full() {
|
||||
let pruned = provider.tx_ref().clear_table::<tables::TransactionHashNumbers>()?;
|
||||
trace!(target: "pruner", %pruned, "Cleared transaction lookup table");
|
||||
|
||||
let last_pruned_block = provider
|
||||
.block_by_transaction_id(end)?
|
||||
.ok_or(PrunerError::InconsistentData("Block for transaction is not found"))?;
|
||||
|
||||
return Ok(SegmentOutput {
|
||||
progress: PruneProgress::Finished,
|
||||
pruned,
|
||||
checkpoint: Some(SegmentOutputCheckpoint {
|
||||
block_number: Some(last_pruned_block),
|
||||
tx_number: Some(end),
|
||||
}),
|
||||
});
|
||||
}
|
||||
|
||||
let tx_range = start..=
|
||||
Some(end)
|
||||
.min(
|
||||
|
||||
Reference in New Issue
Block a user