Skip to content

Commit e859478

Browse files
ch4r10t33rsyjn99KolbyML
authored
feat: Initial version of a key generation utility for ream (#757)
* Feat: Adding message_types.rs * feat: parallelise key generation * feat: amended generate_keys function to create multiple keys based on index * fix: resolved udeps error * feat: Added struct definitions for post quantum keystore * feat: Saving to QsKeystore * feat: Added passphrase parameter to account_manager command * fix: review comments * fix: fixed cargo fmt issue * fix: removed ascii art * fix: fixed review comments * Fix: addressed review comments. * Fix: review comment fixes * fix: linting errors * Fix: Update bin/ream/src/main.rs Co-authored-by: Jun Song <[email protected]> * Fix: Update crates/common/account_manager/src/keystore.rs Co-authored-by: Jun Song <[email protected]> * Fix: Update crates/common/account_manager/src/keystore.rs Co-authored-by: Jun Song <[email protected]> * Fix: review comment fixes * fix: fixed issues with build and removed redundant code * Fix: review comment fixes * fix: Update bin/ream/src/cli/account_manager.rs Co-authored-by: Kolby Moroz Liebl <[email protected]> * Fix: Update bin/ream/src/cli/account_manager.rs Co-authored-by: Kolby Moroz Liebl <[email protected]> * fix: Update crates/common/account_manager/src/lib.rs Co-authored-by: Kolby Moroz Liebl <[email protected]> * Fix: Update crates/common/account_manager/src/message_types.rs Co-authored-by: Kolby Moroz Liebl <[email protected]> * Fix: updated code to address comments * fix: review comment fixes * fix: Removed parallel processing. * Fix: Removed rayon from Cargo.toml * Fix: addressed review comments * fix: renamed functions * fix: changed the default keystore path --------- Co-authored-by: Jun Song <[email protected]> Co-authored-by: Kolby Moroz Liebl <[email protected]>
1 parent e04d438 commit e859478

File tree

13 files changed

+601
-48
lines changed

13 files changed

+601
-48
lines changed

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,3 +27,6 @@ testing/ef-tests/mainnet/*
2727

2828
# DS_Store: Desktop Services Store
2929
.DS_Store
30+
31+
# keystore
32+
.keystore

Cargo.lock

Lines changed: 51 additions & 6 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ alloy-rpc-types-beacon = "1.0.8"
7272
alloy-rpc-types-eth = "1.0.7"
7373
anyhow = "1.0"
7474
async-trait = "0.1.86"
75-
bip32 = "0.5.3"
75+
bip39 = "2.2.0"
7676
clap = "4"
7777
delay_map = "0.4.1"
7878
directories = { version = "6.0.0" }
@@ -86,6 +86,7 @@ eventsource-client = "0.15.0"
8686
futures = "0.3"
8787
hashbrown = "0.15.3"
8888
hashsig = { git = "https://github.com/b-wagn/hash-sig", rev = "287517a763edba7e518b0c1ee5beb868f26f1f66" }
89+
hex = "0.4"
8990
itertools = "0.14"
9091
jsonwebtoken = "9.3.1"
9192
kzg = { git = "https://github.com/grandinetech/rust-kzg" }

bin/ream/Cargo.toml

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,13 +17,15 @@ path = "src/main.rs"
1717
[dependencies]
1818
alloy-primitives.workspace = true
1919
anyhow.workspace = true
20+
bip39.workspace = true
2021
clap = { workspace = true, features = ["derive", "env"] }
2122
discv5.workspace = true
2223
hashbrown.workspace = true
2324
libp2p-identity.workspace = true
2425
prometheus_exporter.workspace = true
2526
rand.workspace = true
2627
rand_chacha.workspace = true
28+
serde_json.workspace = true
2729
tokio.workspace = true
2830
tracing = { workspace = true, features = ["log"] }
2931
tracing-subscriber = { workspace = true, features = ["env-filter"] }

bin/ream/src/cli/account_manager.rs

Lines changed: 29 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
use anyhow::ensure;
2+
use bip39::Mnemonic;
23
use clap::Parser;
4+
use tracing::info;
35

4-
const MIN_CHUNK_SIZE: u64 = 4;
5-
const MIN_LIFETIME: u64 = 18;
6-
const DEFAULT_ACTIVATION_EPOCH: usize = 0;
7-
const DEFAULT_NUM_ACTIVE_EPOCHS: usize = 1 << 18;
6+
const MIN_CHUNK_SIZE: u32 = 4;
7+
const MIN_LIFETIME: u32 = 18;
8+
const DEFAULT_ACTIVATION_EPOCH: u32 = 0;
9+
const DEFAULT_NUM_ACTIVE_EPOCHS: u32 = 1 << 18;
810

911
#[derive(Debug, Parser)]
1012
pub struct AccountManagerConfig {
@@ -14,23 +16,31 @@ pub struct AccountManagerConfig {
1416

1517
/// Account lifetime in 2 ** lifetime slots
1618
#[arg(short, long, default_value_t = 18)]
17-
pub lifetime: u64,
19+
pub lifetime: u32,
1820

1921
/// Chunk size for messages
2022
#[arg(short, long, default_value_t = 5)]
21-
pub chunk_size: u64,
23+
pub chunk_size: u32,
2224

2325
/// Seed phrase for key generation
2426
#[arg(short, long)]
2527
pub seed_phrase: Option<String>,
2628

29+
/// Optional BIP39 passphrase used with the seed phrase
30+
#[arg(long)]
31+
pub passphrase: Option<String>,
32+
2733
/// Activation epoch for the validator
2834
#[arg(long, default_value_t = DEFAULT_ACTIVATION_EPOCH)]
29-
pub activation_epoch: usize,
35+
pub activation_epoch: u32,
3036

3137
/// Number of active epochs
3238
#[arg(long, default_value_t = DEFAULT_NUM_ACTIVE_EPOCHS)]
33-
pub num_active_epochs: usize,
39+
pub num_active_epochs: u32,
40+
41+
/// Path for keystore directory (relative to data-dir if not absolute)
42+
#[arg(long)]
43+
pub keystore_path: Option<String>,
3444
}
3545

3646
impl Default for AccountManagerConfig {
@@ -40,8 +50,10 @@ impl Default for AccountManagerConfig {
4050
lifetime: 18,
4151
chunk_size: 5,
4252
seed_phrase: None,
53+
passphrase: None,
4354
activation_epoch: DEFAULT_ACTIVATION_EPOCH,
4455
num_active_epochs: DEFAULT_NUM_ACTIVE_EPOCHS,
56+
keystore_path: None,
4557
}
4658
}
4759
}
@@ -60,14 +72,22 @@ impl AccountManagerConfig {
6072
self.lifetime >= MIN_LIFETIME,
6173
"Lifetime must be at least {MIN_LIFETIME}"
6274
);
75+
6376
Ok(())
6477
}
6578

6679
pub fn get_seed_phrase(&self) -> String {
6780
if let Some(phrase) = &self.seed_phrase {
6881
phrase.clone()
6982
} else {
70-
"default_seed_phrase".to_string()
83+
// Generate a new BIP39 mnemonic with 24 words (256 bits of entropy)
84+
let entropy: [u8; 32] = rand::random();
85+
let mnemonic = Mnemonic::from_entropy(&entropy).expect("Failed to generate mnemonic");
86+
let phrase = mnemonic.words().collect::<Vec<_>>().join(" ");
87+
info!("{}", "=".repeat(89));
88+
info!("Generated new seed phrase (KEEP SAFE): {phrase}");
89+
info!("{}", "=".repeat(89));
90+
phrase
7191
}
7292
}
7393
}

0 commit comments

Comments
 (0)