reth_node_core/args/
dev.rs

1//! clap [Args](clap::Args) for Dev testnet configuration
2
3use std::time::Duration;
4
5use clap::Args;
6use humantime::parse_duration;
7
8const DEFAULT_MNEMONIC: &str = "test test test test test test test test test test test junk";
9
10/// Parameters for Dev testnet configuration
11#[derive(Debug, Args, PartialEq, Eq, Clone)]
12#[command(next_help_heading = "Dev testnet")]
13pub struct DevArgs {
14    /// Start the node in dev mode
15    ///
16    /// This mode uses a local proof-of-authority consensus engine with either fixed block times
17    /// or automatically mined blocks.
18    /// Disables network discovery and enables local http server.
19    /// Prefunds 20 accounts derived by mnemonic "test test test test test test test test test test
20    /// test junk" with 10 000 ETH each.
21    #[arg(long = "dev", alias = "auto-mine", help_heading = "Dev testnet", verbatim_doc_comment)]
22    pub dev: bool,
23
24    /// How many transactions to mine per block.
25    #[arg(
26        long = "dev.block-max-transactions",
27        help_heading = "Dev testnet",
28        conflicts_with = "block_time"
29    )]
30    pub block_max_transactions: Option<usize>,
31
32    /// Interval between blocks.
33    ///
34    /// Parses strings using [`humantime::parse_duration`]
35    /// --dev.block-time 12s
36    #[arg(
37        long = "dev.block-time",
38        help_heading = "Dev testnet",
39        conflicts_with = "block_max_transactions",
40        value_parser = parse_duration,
41        verbatim_doc_comment
42    )]
43    pub block_time: Option<Duration>,
44
45    /// Derive dev accounts from a fixed mnemonic instead of random ones.
46    #[arg(
47        long = "dev.mnemonic",
48        help_heading = "Dev testnet",
49        value_name = "MNEMONIC",
50        requires = "dev",
51        verbatim_doc_comment,
52        default_value = DEFAULT_MNEMONIC
53    )]
54    pub dev_mnemonic: String,
55}
56
57impl Default for DevArgs {
58    fn default() -> Self {
59        Self {
60            dev: false,
61            block_max_transactions: None,
62            block_time: None,
63            dev_mnemonic: DEFAULT_MNEMONIC.to_string(),
64        }
65    }
66}
67
68#[cfg(test)]
69mod tests {
70    use super::*;
71    use clap::Parser;
72
73    /// A helper type to parse Args more easily
74    #[derive(Parser)]
75    struct CommandParser<T: Args> {
76        #[command(flatten)]
77        args: T,
78    }
79
80    #[test]
81    fn test_parse_dev_args() {
82        let args = CommandParser::<DevArgs>::parse_from(["reth"]).args;
83        assert_eq!(
84            args,
85            DevArgs {
86                dev: false,
87                block_max_transactions: None,
88                block_time: None,
89                dev_mnemonic: DEFAULT_MNEMONIC.to_string(),
90            }
91        );
92
93        let args = CommandParser::<DevArgs>::parse_from(["reth", "--dev"]).args;
94        assert_eq!(
95            args,
96            DevArgs {
97                dev: true,
98                block_max_transactions: None,
99                block_time: None,
100                dev_mnemonic: DEFAULT_MNEMONIC.to_string(),
101            }
102        );
103
104        let args = CommandParser::<DevArgs>::parse_from(["reth", "--auto-mine"]).args;
105        assert_eq!(
106            args,
107            DevArgs {
108                dev: true,
109                block_max_transactions: None,
110                block_time: None,
111                dev_mnemonic: DEFAULT_MNEMONIC.to_string(),
112            }
113        );
114
115        let args = CommandParser::<DevArgs>::parse_from([
116            "reth",
117            "--dev",
118            "--dev.block-max-transactions",
119            "2",
120        ])
121        .args;
122        assert_eq!(
123            args,
124            DevArgs {
125                dev: true,
126                block_max_transactions: Some(2),
127                block_time: None,
128                dev_mnemonic: DEFAULT_MNEMONIC.to_string(),
129            }
130        );
131
132        let args =
133            CommandParser::<DevArgs>::parse_from(["reth", "--dev", "--dev.block-time", "1s"]).args;
134        assert_eq!(
135            args,
136            DevArgs {
137                dev: true,
138                block_max_transactions: None,
139                block_time: Some(std::time::Duration::from_secs(1)),
140                dev_mnemonic: DEFAULT_MNEMONIC.to_string(),
141            }
142        );
143    }
144
145    #[test]
146    fn test_parse_dev_args_conflicts() {
147        let args = CommandParser::<DevArgs>::try_parse_from([
148            "reth",
149            "--dev",
150            "--dev.block-max-transactions",
151            "2",
152            "--dev.block-time",
153            "1s",
154        ]);
155        assert!(args.is_err());
156    }
157
158    #[test]
159    fn dev_args_default_sanity_check() {
160        let default_args = DevArgs::default();
161        let args = CommandParser::<DevArgs>::parse_from(["reth"]).args;
162        assert_eq!(args, default_args);
163    }
164}