Skip to main content

mina_node/daemon_json/
mod.rs

1use mina_core::constants::ForkConstants;
2use serde::{Deserialize, Serialize};
3
4mod json_daemon;
5mod json_genesis;
6mod json_ledger;
7pub use json_daemon::Daemon;
8pub use json_genesis::Genesis;
9pub use json_ledger::{
10    build_ledger_name, Account, AccountConfigError, AccountPermissions, AccountTiming, Ledger,
11    Zkapp,
12};
13
14/// This type represents a JSON object loaded from daemon.json
15/// file. It does not describe its full structure, as it's not
16/// necessary for our purpose here. We only need to extract
17/// certain information from it.
18/// In practice, this format is never really used to convey
19/// the network's configuration, as the standard practice is to
20/// compile that into the OCaml node's binary.
21/// In theory, though, the underlying JSON file could contain
22/// more information that the following format describes. If
23/// that happens, the format can be extended to accommodate.
24#[derive(Debug, Clone, Serialize, Deserialize)]
25pub struct DaemonJson {
26    pub daemon: Option<Daemon>,
27    pub ledger: Option<Ledger>,
28    pub genesis: Option<Genesis>,
29    pub epoch_data: Option<Epochs>,
30    pub proof: Option<Proof>,
31}
32
33#[derive(Debug, Clone, Serialize, Deserialize)]
34pub struct Epochs {
35    pub staking: EpochData,
36    pub next: Option<EpochData>,
37}
38
39#[derive(Debug, Clone, Serialize, Deserialize)]
40pub struct EpochData {
41    pub accounts: Option<Vec<Account>>,
42    pub hash: Option<String>,
43    pub s3_data_hash: Option<String>,
44    pub seed: String,
45}
46
47#[derive(Debug, Clone, Serialize, Deserialize)]
48pub struct Proof {
49    pub fork: Option<ForkConstants>,
50}
51
52impl EpochData {
53    pub fn ledger_name(&self) -> String {
54        self.hash.clone().unwrap_or_else(|| {
55            build_ledger_name(
56                self.accounts.as_ref().map(Vec::len).unwrap_or(0),
57                self.accounts
58                    .clone()
59                    .unwrap_or_default()
60                    .iter()
61                    .map(|a| a.balance.clone())
62                    .enumerate(),
63            )
64        })
65    }
66}
67
68#[cfg(test)]
69mod test {
70
71    use ledger::{scan_state::currency::Balance, Timing};
72    use mina_node_account::AccountPublicKey;
73    use std::str::FromStr;
74
75    use crate::daemon_json::DaemonJson;
76
77    #[test]
78    fn test_daemon_json_read() {
79        let test_filename = "testing/data/daemon.json";
80        println!(
81            "Reading from: {}",
82            std::env::current_dir().unwrap().display()
83        );
84        let test_file = std::fs::File::open(test_filename).unwrap();
85        let daemon_json: DaemonJson = serde_json::from_reader(test_file).unwrap();
86        let ledger = daemon_json.ledger.unwrap();
87        assert_eq!(ledger.name, Some("devnet".to_string()));
88        let addr1 =
89            AccountPublicKey::from_str("B62qnLVz8wM7MfJsuYbjFf4UWbwrUBEL5ZdawExxxFhnGXB6siqokyM")
90                .unwrap();
91        let acc1 = ledger.find_account(&addr1).unwrap();
92        assert_eq!(acc1.balance(), Balance::from_u64(83_333_000_000_000));
93        assert_eq!(acc1.delegate().unwrap(), Some(acc1.public_key().unwrap()));
94        assert!(acc1.secret_key().unwrap().is_none());
95        assert_eq!(acc1.timing().unwrap(), Timing::Untimed);
96        let addr2 =
97            AccountPublicKey::from_str("B62qnJcRzJpdaXvi6ok3iH7BbP3R6oZtT1C9qTyUr9hNHWRf3eUAJxC")
98                .unwrap();
99        let acc2 = ledger.find_account(&addr2).unwrap();
100        assert_eq!(acc2.balance(), Balance::from_u64(2_000_000_000_000_000));
101        assert_eq!(acc2.delegate().unwrap(), Some(acc1.public_key().unwrap()));
102        if let Timing::Timed {
103            initial_minimum_balance,
104            ..
105        } = acc2.timing().unwrap()
106        {
107            assert_eq!(
108                initial_minimum_balance,
109                Balance::from_u64(1_000_000_000_000_000)
110            );
111        } else {
112            panic!("Expected Timed account");
113        }
114        let daemon = daemon_json.daemon.unwrap();
115        assert_eq!(daemon.tx_pool_max_size(), 3000);
116        assert_eq!(daemon.peer_list_url(), None);
117        assert_eq!(daemon.slot_tx_end(), None);
118        assert_eq!(daemon.slot_chain_end(), None);
119    }
120}