hotshot_builder_refactored/
block_store.rs

1use std::marker::PhantomData;
2
3use hotshot::traits::BlockPayload;
4use hotshot_builder_api::v0_1::block_info::AvailableBlockInfo;
5use hotshot_builder_shared::{
6    block::{BlockId, BuilderStateId},
7    coordinator::tiered_view_map::TieredViewMap,
8    error::Error,
9    utils::BuilderKeys,
10};
11use hotshot_types::traits::{node_implementation::NodeType, signature_key::BuilderSignatureKey};
12
13// It holds all the necessary information for a block
14#[derive(Debug, Clone)]
15pub struct BlockInfo<Types: NodeType> {
16    pub block_payload: Types::BlockPayload,
17    pub metadata: <<Types as NodeType>::BlockPayload as BlockPayload<Types>>::Metadata,
18    pub block_size: u64,
19    pub offered_fee: u64,
20    // Could we have included more transactions with this block, but chose not to?
21    pub truncated: bool,
22}
23
24impl<Types: NodeType> BlockInfo<Types> {
25    pub fn signed_response(
26        &self,
27        keys: &BuilderKeys<Types>,
28    ) -> Result<AvailableBlockInfo<Types>, Error<Types>> {
29        let block_hash = self.block_payload.builder_commitment(&self.metadata);
30        let signature = <Types as NodeType>::BuilderSignatureKey::sign_block_info(
31            &keys.1,
32            self.block_size,
33            self.offered_fee,
34            &block_hash,
35        )
36        .map_err(Error::Signing)?;
37        Ok(AvailableBlockInfo {
38            block_hash,
39            block_size: self.block_size,
40            offered_fee: self.offered_fee,
41            signature,
42            sender: keys.0.clone(),
43            _phantom: PhantomData,
44        })
45    }
46}
47
48#[derive(Default)]
49pub struct BlockStore<Types: NodeType> {
50    pub(crate) blocks: TieredViewMap<BlockId<Types>, BlockInfo<Types>>,
51    pub(crate) block_cache: TieredViewMap<BuilderStateId<Types>, BlockId<Types>>,
52}
53
54impl<Types: NodeType> BlockStore<Types> {
55    pub fn new() -> Self {
56        Self::default()
57    }
58
59    pub fn update(
60        &mut self,
61        built_by: BuilderStateId<Types>,
62        block_id: BlockId<Types>,
63        block_info: BlockInfo<Types>,
64    ) {
65        self.blocks.insert(block_id.clone(), block_info);
66        self.block_cache.insert(built_by, block_id);
67    }
68
69    pub fn get_cached(&self, builder_id: &BuilderStateId<Types>) -> Option<&BlockInfo<Types>> {
70        let block_id = self.block_cache.get(builder_id)?;
71        self.blocks.get(block_id)
72    }
73
74    pub fn get_block(&self, block_id: &BlockId<Types>) -> Option<&BlockInfo<Types>> {
75        self.blocks.get(block_id)
76    }
77
78    pub fn prune(&mut self, cutoff: Types::View) {
79        self.blocks.prune(cutoff);
80        self.block_cache.prune(cutoff);
81    }
82}