reth_static_file/segments/
headers.rs
1use crate::segments::Segment;
2use alloy_primitives::BlockNumber;
3use reth_codecs::Compact;
4use reth_db_api::{cursor::DbCursorRO, table::Value, tables, transaction::DbTx};
5use reth_primitives_traits::NodePrimitives;
6use reth_provider::{providers::StaticFileWriter, DBProvider, StaticFileProviderFactory};
7use reth_static_file_types::StaticFileSegment;
8use reth_storage_errors::provider::ProviderResult;
9use std::ops::RangeInclusive;
10
11#[derive(Debug, Default)]
13pub struct Headers;
14
15impl<Provider> Segment<Provider> for Headers
16where
17 Provider: StaticFileProviderFactory<Primitives: NodePrimitives<BlockHeader: Compact + Value>>
18 + DBProvider,
19{
20 fn segment(&self) -> StaticFileSegment {
21 StaticFileSegment::Headers
22 }
23
24 fn copy_to_static_files(
25 &self,
26 provider: Provider,
27 block_range: RangeInclusive<BlockNumber>,
28 ) -> ProviderResult<()> {
29 let static_file_provider = provider.static_file_provider();
30 let mut static_file_writer =
31 static_file_provider.get_writer(*block_range.start(), StaticFileSegment::Headers)?;
32
33 let mut headers_cursor = provider
34 .tx_ref()
35 .cursor_read::<tables::Headers<<Provider::Primitives as NodePrimitives>::BlockHeader>>(
36 )?;
37 let headers_walker = headers_cursor.walk_range(block_range.clone())?;
38
39 let mut header_td_cursor =
40 provider.tx_ref().cursor_read::<tables::HeaderTerminalDifficulties>()?;
41 let header_td_walker = header_td_cursor.walk_range(block_range.clone())?;
42
43 let mut canonical_headers_cursor =
44 provider.tx_ref().cursor_read::<tables::CanonicalHeaders>()?;
45 let canonical_headers_walker = canonical_headers_cursor.walk_range(block_range)?;
46
47 for ((header_entry, header_td_entry), canonical_header_entry) in
48 headers_walker.zip(header_td_walker).zip(canonical_headers_walker)
49 {
50 let (header_block, header) = header_entry?;
51 let (header_td_block, header_td) = header_td_entry?;
52 let (canonical_header_block, canonical_header) = canonical_header_entry?;
53
54 debug_assert_eq!(header_block, header_td_block);
55 debug_assert_eq!(header_td_block, canonical_header_block);
56
57 static_file_writer.append_header(&header, header_td.0, &canonical_header)?;
58 }
59
60 Ok(())
61 }
62}