espresso_node/persistence/
no_storage.rs

1//! Mock implementation of persistence, for testing.
2use std::{collections::BTreeMap, sync::Arc};
3
4use anyhow::bail;
5use async_trait::async_trait;
6use espresso_types::{
7    AuthenticatedValidatorMap, Leaf2, NetworkConfig, PubKey, RegisteredValidatorMap,
8    StakeTableHash,
9    traits::{EventsPersistenceRead, MembershipPersistence, StakeTuple},
10    v0::traits::{EventConsumer, PersistenceOptions, SequencerPersistence},
11    v0_3::{EventKey, IndexedStake, RegisteredValidator, RewardAmount, StakeTableEvent},
12};
13use hotshot::InitializerEpochInfo;
14use hotshot_libp2p_networking::network::behaviours::dht::store::persistent::{
15    DhtPersistentStorage, SerializableRecord,
16};
17use hotshot_types::{
18    data::{
19        DaProposal, DaProposal2, EpochNumber, QuorumProposalWrapper, VidCommitment,
20        VidDisperseShare,
21    },
22    drb::{DrbInput, DrbResult},
23    event::{Event, EventType, HotShotAction, LeafInfo},
24    message::Proposal,
25    simple_certificate::{
26        CertificatePair, LightClientStateUpdateCertificateV2, NextEpochQuorumCertificate2,
27        QuorumCertificate2, UpgradeCertificate,
28    },
29    traits::metrics::Metrics,
30    vote::HasViewNumber,
31};
32
33use crate::{NodeType, SeqTypes, ViewNumber};
34
35#[derive(Clone, Copy, Debug)]
36pub struct Options;
37
38#[async_trait]
39impl PersistenceOptions for Options {
40    type Persistence = NoStorage;
41
42    fn set_view_retention(&mut self, _: u64) {}
43
44    async fn create(&mut self) -> anyhow::Result<Self::Persistence> {
45        Ok(NoStorage)
46    }
47
48    async fn reset(self) -> anyhow::Result<()> {
49        Ok(())
50    }
51}
52
53#[derive(Clone, Copy, Debug)]
54pub struct NoStorage;
55
56#[async_trait]
57impl SequencerPersistence for NoStorage {
58    async fn migrate_reward_merkle_tree_v2(&self) -> anyhow::Result<()> {
59        Ok(())
60    }
61
62    async fn load_config(&self) -> anyhow::Result<Option<NetworkConfig>> {
63        Ok(None)
64    }
65
66    async fn save_config(&self, _: &NetworkConfig) -> anyhow::Result<()> {
67        Ok(())
68    }
69
70    async fn append_decided_leaves(
71        &self,
72        view_number: ViewNumber,
73        leaves: impl IntoIterator<Item = (&LeafInfo<SeqTypes>, CertificatePair<SeqTypes>)> + Send,
74        deciding_qc: Option<Arc<CertificatePair<SeqTypes>>>,
75        consumer: &impl EventConsumer,
76    ) -> anyhow::Result<()> {
77        let leaves = leaves
78            .into_iter()
79            .map(|(info_ref, qc)| (info_ref.clone(), qc))
80            .collect::<Vec<_>>();
81        for (leaf_info, qc) in leaves {
82            // Insert the deciding QC at the appropriate position, with the last decide event in the
83            // chain.
84            let deciding_qc = if let Some(deciding_qc) = &deciding_qc {
85                (deciding_qc.view_number() == qc.view_number() + 1).then_some(deciding_qc.clone())
86            } else {
87                None
88            };
89
90            consumer
91                .handle_event(&Event {
92                    view_number,
93                    event: EventType::Decide {
94                        leaf_chain: Arc::new(vec![leaf_info.clone()]),
95                        committing_qc: Arc::new(qc),
96                        deciding_qc,
97                        block_size: None,
98                    },
99                })
100                .await?;
101        }
102        Ok(())
103    }
104
105    async fn load_latest_acted_view(&self) -> anyhow::Result<Option<ViewNumber>> {
106        Ok(None)
107    }
108
109    async fn load_restart_view(&self) -> anyhow::Result<Option<ViewNumber>> {
110        Ok(None)
111    }
112
113    async fn load_anchor_leaf(
114        &self,
115    ) -> anyhow::Result<Option<(Leaf2, QuorumCertificate2<SeqTypes>)>> {
116        Ok(None)
117    }
118
119    async fn load_da_proposal(
120        &self,
121        _view: ViewNumber,
122    ) -> anyhow::Result<Option<Proposal<SeqTypes, DaProposal2<SeqTypes>>>> {
123        Ok(None)
124    }
125
126    async fn load_vid_share(
127        &self,
128        _view: ViewNumber,
129    ) -> anyhow::Result<Option<Proposal<SeqTypes, VidDisperseShare<SeqTypes>>>> {
130        Ok(None)
131    }
132
133    async fn load_quorum_proposals(
134        &self,
135    ) -> anyhow::Result<BTreeMap<ViewNumber, Proposal<SeqTypes, QuorumProposalWrapper<SeqTypes>>>>
136    {
137        Ok(Default::default())
138    }
139    async fn load_quorum_proposal(
140        &self,
141        view: ViewNumber,
142    ) -> anyhow::Result<Proposal<SeqTypes, QuorumProposalWrapper<SeqTypes>>> {
143        bail!("proposal {view:?} not available");
144    }
145    async fn load_upgrade_certificate(
146        &self,
147    ) -> anyhow::Result<Option<UpgradeCertificate<SeqTypes>>> {
148        Ok(None)
149    }
150
151    async fn append_vid(
152        &self,
153        _proposal: &Proposal<SeqTypes, VidDisperseShare<SeqTypes>>,
154    ) -> anyhow::Result<()> {
155        Ok(())
156    }
157    async fn append_da(
158        &self,
159        _proposal: &Proposal<SeqTypes, DaProposal<SeqTypes>>,
160        _vid_commit: VidCommitment,
161    ) -> anyhow::Result<()> {
162        Ok(())
163    }
164    async fn record_action(
165        &self,
166        _view: ViewNumber,
167        _epoch: Option<EpochNumber>,
168        _action: HotShotAction,
169    ) -> anyhow::Result<()> {
170        Ok(())
171    }
172    async fn append_quorum_proposal2(
173        &self,
174        _proposal: &Proposal<SeqTypes, QuorumProposalWrapper<SeqTypes>>,
175    ) -> anyhow::Result<()> {
176        Ok(())
177    }
178    async fn store_upgrade_certificate(
179        &self,
180        _decided_upgrade_certificate: Option<UpgradeCertificate<SeqTypes>>,
181    ) -> anyhow::Result<()> {
182        Ok(())
183    }
184
185    async fn store_next_epoch_quorum_certificate(
186        &self,
187        _high_qc: NextEpochQuorumCertificate2<SeqTypes>,
188    ) -> anyhow::Result<()> {
189        Ok(())
190    }
191
192    async fn load_next_epoch_quorum_certificate(
193        &self,
194    ) -> anyhow::Result<Option<NextEpochQuorumCertificate2<SeqTypes>>> {
195        Ok(None)
196    }
197
198    async fn store_eqc(
199        &self,
200        _high_qc: QuorumCertificate2<SeqTypes>,
201        _next_epoch_high_qc: NextEpochQuorumCertificate2<SeqTypes>,
202    ) -> anyhow::Result<()> {
203        Ok(())
204    }
205
206    async fn load_eqc(
207        &self,
208    ) -> Option<(
209        QuorumCertificate2<SeqTypes>,
210        NextEpochQuorumCertificate2<SeqTypes>,
211    )> {
212        None
213    }
214
215    async fn append_da2(
216        &self,
217        _proposal: &Proposal<SeqTypes, DaProposal2<SeqTypes>>,
218        _vid_commit: VidCommitment,
219    ) -> anyhow::Result<()> {
220        Ok(())
221    }
222
223    async fn append_proposal2(
224        &self,
225        _proposal: &Proposal<SeqTypes, QuorumProposalWrapper<SeqTypes>>,
226    ) -> anyhow::Result<()> {
227        Ok(())
228    }
229
230    async fn migrate_anchor_leaf(&self) -> anyhow::Result<()> {
231        Ok(())
232    }
233
234    async fn migrate_da_proposals(&self) -> anyhow::Result<()> {
235        Ok(())
236    }
237
238    async fn migrate_vid_shares(&self) -> anyhow::Result<()> {
239        Ok(())
240    }
241
242    async fn migrate_quorum_proposals(&self) -> anyhow::Result<()> {
243        Ok(())
244    }
245
246    async fn migrate_quorum_certificates(&self) -> anyhow::Result<()> {
247        Ok(())
248    }
249
250    async fn migrate_x25519_keys(&self) -> anyhow::Result<()> {
251        Ok(())
252    }
253
254    async fn store_drb_result(
255        &self,
256        _epoch: EpochNumber,
257        _drb_result: DrbResult,
258    ) -> anyhow::Result<()> {
259        Ok(())
260    }
261
262    async fn store_drb_input(&self, _drb_input: DrbInput) -> anyhow::Result<()> {
263        Ok(())
264    }
265    async fn load_drb_input(&self, _epoch: u64) -> anyhow::Result<DrbInput> {
266        bail!("Cannot load from NoStorage")
267    }
268
269    async fn store_epoch_root(
270        &self,
271        _epoch: EpochNumber,
272        _block_header: <SeqTypes as NodeType>::BlockHeader,
273    ) -> anyhow::Result<()> {
274        Ok(())
275    }
276
277    async fn load_start_epoch_info(&self) -> anyhow::Result<Vec<InitializerEpochInfo<SeqTypes>>> {
278        Ok(Vec::new())
279    }
280
281    async fn add_state_cert(
282        &self,
283        _state_cert: LightClientStateUpdateCertificateV2<SeqTypes>,
284    ) -> anyhow::Result<()> {
285        Ok(())
286    }
287
288    async fn load_state_cert(
289        &self,
290    ) -> anyhow::Result<Option<LightClientStateUpdateCertificateV2<SeqTypes>>> {
291        Ok(None)
292    }
293
294    async fn get_state_cert_by_epoch(
295        &self,
296        _epoch: u64,
297    ) -> anyhow::Result<Option<LightClientStateUpdateCertificateV2<SeqTypes>>> {
298        Ok(None)
299    }
300
301    async fn insert_state_cert(
302        &self,
303        _epoch: u64,
304        _cert: LightClientStateUpdateCertificateV2<SeqTypes>,
305    ) -> anyhow::Result<()> {
306        Ok(())
307    }
308
309    fn enable_metrics(&mut self, _metrics: &dyn Metrics) {}
310}
311
312#[async_trait]
313impl MembershipPersistence for NoStorage {
314    async fn load_stake(&self, _epoch: EpochNumber) -> anyhow::Result<Option<StakeTuple>> {
315        Ok(None)
316    }
317
318    async fn load_latest_stake(&self, _limit: u64) -> anyhow::Result<Option<Vec<IndexedStake>>> {
319        Ok(None)
320    }
321
322    async fn store_stake(
323        &self,
324        _epoch: EpochNumber,
325        _stake: AuthenticatedValidatorMap,
326        _block_reward: Option<RewardAmount>,
327        _stake_table_hash: Option<StakeTableHash>,
328    ) -> anyhow::Result<()> {
329        Ok(())
330    }
331
332    async fn store_events(
333        &self,
334        _l1: u64,
335        _events: Vec<(EventKey, StakeTableEvent)>,
336    ) -> anyhow::Result<()> {
337        Ok(())
338    }
339    async fn load_events(
340        &self,
341        _from_l1_block: u64,
342        _l1_block: u64,
343    ) -> anyhow::Result<(
344        Option<EventsPersistenceRead>,
345        Vec<(EventKey, StakeTableEvent)>,
346    )> {
347        Ok((None, Vec::new()))
348    }
349
350    async fn delete_stake_tables(&self) -> anyhow::Result<()> {
351        Ok(())
352    }
353
354    async fn store_all_validators(
355        &self,
356        _epoch: EpochNumber,
357        _all_validators: RegisteredValidatorMap,
358    ) -> anyhow::Result<()> {
359        Ok(())
360    }
361
362    async fn load_all_validators(
363        &self,
364        _epoch: EpochNumber,
365        _offset: u64,
366        _limit: u64,
367    ) -> anyhow::Result<Vec<RegisteredValidator<PubKey>>> {
368        Ok(Default::default())
369    }
370}
371
372#[async_trait]
373impl DhtPersistentStorage for NoStorage {
374    /// Don't do anything
375    async fn save(&self, _records: Vec<SerializableRecord>) -> anyhow::Result<()> {
376        Ok(())
377    }
378
379    /// Don't do anything
380    async fn load(&self) -> anyhow::Result<Vec<SerializableRecord>> {
381        Ok(vec![])
382    }
383}