diem_config/config/
test_config.rs

1// Copyright (c) The Diem Core Contributors
2// SPDX-License-Identifier: Apache-2.0
3
4// Copyright 2021 Conflux Foundation. All rights reserved.
5// Conflux is free software and distributed under GNU General Public License.
6// See http://www.gnu.org/licenses/
7
8use crate::keys::ConfigKey;
9use diem_crypto::{ed25519::Ed25519PrivateKey, PrivateKey, Uniform};
10use diem_temppath::TempPath;
11use diem_types::{
12    on_chain_config::VMPublishingOption,
13    transaction::authenticator::AuthenticationKey,
14};
15use rand::rngs::StdRng;
16use serde::{Deserialize, Serialize};
17use std::path::Path;
18
19#[derive(Debug, Default, Deserialize, Serialize)]
20#[serde(deny_unknown_fields)]
21pub struct TestConfig {
22    pub auth_key: Option<AuthenticationKey>,
23    pub operator_key: Option<ConfigKey<Ed25519PrivateKey>>,
24    pub owner_key: Option<ConfigKey<Ed25519PrivateKey>>,
25    pub execution_key: Option<ConfigKey<Ed25519PrivateKey>>,
26    // Used only to prevent a potentially temporary data_dir from being
27    // deleted. This should eventually be moved to be owned by something
28    // outside the config.
29    #[serde(skip)]
30    temp_dir: Option<TempPath>,
31
32    pub publishing_option: Option<VMPublishingOption>,
33}
34
35impl Clone for TestConfig {
36    fn clone(&self) -> Self {
37        Self {
38            auth_key: self.auth_key,
39            operator_key: self.operator_key.clone(),
40            owner_key: self.owner_key.clone(),
41            execution_key: self.execution_key.clone(),
42            temp_dir: None,
43            publishing_option: self.publishing_option.clone(),
44        }
45    }
46}
47
48impl PartialEq for TestConfig {
49    fn eq(&self, other: &Self) -> bool {
50        self.operator_key == other.operator_key
51            && self.owner_key == other.owner_key
52            && self.auth_key == other.auth_key
53            && self.execution_key == other.execution_key
54    }
55}
56
57impl TestConfig {
58    pub fn open_module() -> Self {
59        Self {
60            auth_key: None,
61            operator_key: None,
62            owner_key: None,
63            execution_key: None,
64            temp_dir: None,
65            publishing_option: Some(VMPublishingOption::open()),
66        }
67    }
68
69    pub fn new_with_temp_dir(temp_dir: Option<TempPath>) -> Self {
70        let temp_dir = temp_dir.unwrap_or_else(|| {
71            let temp_dir = TempPath::new();
72            temp_dir.create_as_dir().expect("error creating tempdir");
73            temp_dir
74        });
75        Self {
76            auth_key: None,
77            operator_key: None,
78            owner_key: None,
79            execution_key: None,
80            temp_dir: Some(temp_dir),
81            publishing_option: None,
82        }
83    }
84
85    pub fn execution_key(&mut self, key: Ed25519PrivateKey) {
86        self.execution_key = Some(ConfigKey::new(key))
87    }
88
89    pub fn operator_key(&mut self, key: Ed25519PrivateKey) {
90        self.operator_key = Some(ConfigKey::new(key))
91    }
92
93    pub fn owner_key(&mut self, key: Ed25519PrivateKey) {
94        self.owner_key = Some(ConfigKey::new(key))
95    }
96
97    pub fn random_account_key(&mut self, rng: &mut StdRng) {
98        let privkey = Ed25519PrivateKey::generate(rng);
99        self.auth_key = Some(AuthenticationKey::ed25519(&privkey.public_key()));
100        self.operator_key = Some(ConfigKey::new(privkey));
101
102        let privkey = Ed25519PrivateKey::generate(rng);
103        self.owner_key = Some(ConfigKey::new(privkey));
104    }
105
106    pub fn random_execution_key(&mut self, rng: &mut StdRng) {
107        let privkey = Ed25519PrivateKey::generate(rng);
108        self.execution_key = Some(ConfigKey::new(privkey));
109    }
110
111    pub fn temp_dir(&self) -> Option<&Path> {
112        self.temp_dir.as_ref().map(|temp_dir| temp_dir.path())
113    }
114}
115
116#[cfg(test)]
117mod test {
118    use super::*;
119    use rand::{rngs::StdRng, SeedableRng};
120
121    #[test]
122    fn verify_test_config_equality_using_keys() {
123        // Create default test config without keys
124        let mut test_config = TestConfig::new_with_temp_dir(None);
125        assert_eq!(test_config.operator_key, None);
126        assert_eq!(test_config.owner_key, None);
127        assert_eq!(test_config.execution_key, None);
128
129        // Clone the config and verify equality
130        let mut clone_test_config = test_config.clone();
131        assert_eq!(clone_test_config, test_config);
132
133        // Generate keys for original test config
134        let mut rng = StdRng::from_seed([0u8; 32]);
135        test_config.random_account_key(&mut rng);
136        test_config.random_execution_key(&mut rng);
137
138        // Verify that configs differ
139        assert_ne!(clone_test_config, test_config);
140
141        // Copy keys across configs
142        clone_test_config.auth_key = test_config.auth_key;
143        clone_test_config.execution_key = test_config.execution_key.clone();
144        clone_test_config.operator_key = test_config.operator_key.clone();
145        clone_test_config.owner_key = test_config.owner_key.clone();
146
147        // Verify both configs are identical
148        assert_eq!(clone_test_config, test_config);
149    }
150}