1use crate::{
2 TempoEvmConfig, TempoEvmFactory, block::TempoReceiptBuilder, context::TempoBlockExecutionCtx,
3};
4use alloy_evm::{block::BlockExecutionError, eth::EthBlockExecutorFactory};
5use reth_evm::execute::{BlockAssembler, BlockAssemblerInput};
6use reth_evm_ethereum::EthBlockAssembler;
7use reth_primitives_traits::SealedHeader;
8use std::sync::Arc;
9use tempo_chainspec::TempoChainSpec;
10use tempo_primitives::TempoHeader;
11
12#[derive(Debug, Clone)]
14pub struct TempoBlockAssembler {
15 pub(crate) inner: EthBlockAssembler<TempoChainSpec>,
16}
17
18impl TempoBlockAssembler {
19 pub fn new(chain_spec: Arc<TempoChainSpec>) -> Self {
20 Self {
21 inner: EthBlockAssembler::new(chain_spec),
22 }
23 }
24}
25
26impl BlockAssembler<TempoEvmConfig> for TempoBlockAssembler {
27 type Block = tempo_primitives::Block;
28
29 fn assemble_block(
30 &self,
31 input: BlockAssemblerInput<'_, '_, TempoEvmConfig, TempoHeader>,
32 ) -> Result<Self::Block, BlockExecutionError> {
33 let BlockAssemblerInput {
34 evm_env,
35 execution_ctx:
36 TempoBlockExecutionCtx {
37 inner,
38 general_gas_limit,
39 extra_data,
40 shared_gas_limit,
41 validator_set: _,
42 subblock_fee_recipients: _,
43 },
44 parent,
45 transactions,
46 output,
47 bundle_state,
48 state_provider,
49 state_root,
50 ..
51 } = input;
52
53 let parent = SealedHeader::new_unhashed(parent.clone().into_header().inner);
54
55 let timestamp_millis_part = evm_env.block_env.timestamp_millis_part;
56
57 let mut assembler = self.inner.clone();
59 assembler.extra_data = extra_data;
60
61 let block = assembler.assemble_block(BlockAssemblerInput::<
63 EthBlockExecutorFactory<TempoReceiptBuilder, TempoChainSpec, TempoEvmFactory>,
64 >::new(
65 evm_env,
66 inner,
67 &parent,
68 transactions,
69 output,
70 bundle_state,
71 state_provider,
72 state_root,
73 ))?;
74
75 Ok(block.map_header(|inner| TempoHeader {
76 inner,
77 general_gas_limit,
78 timestamp_millis_part,
79 shared_gas_limit,
80 }))
81 }
82}