src/wallets/structures.rs
// basic struct for address
#[derive(Serialize, Deserialize)]
pub struct Wallet {
pub address: String,
pub public_key: String,
pub private_key: String,
}
// enum for address in case we change addresses at a later time
#[derive(Serialize, Deserialize)]
pub enum AddressPrefix {
Original,
}
// set the original prefix to TAC
impl AddressPrefix {
pub fn to_string(&self) -> &'static str {
match *self {
AddressPrefix::Original => "TAC",
}
}
}
src/wallets/create_keys.rs
// generate the public key and the private key
pub fn generate_keypair() -> (Vec<u8>, String) {
let secp = Secp256k1::new();
let mut rng = OsRng::default(); // Create an instance of OsRng
let mut secret_key_bytes: Vec<u8> = vec![0; 32];
rng.fill_bytes(&mut secret_key_bytes);
let secret_key = SecretKey::from_slice(&secret_key_bytes)
.expect("Failed to create SecretKey from random bytes");
let public_key = PublicKey::from_secret_key(&secp, &secret_key);
let public_key_bytes = public_key.serialize().to_vec();
let private_key_hex = hex::encode(secret_key_bytes);
(public_key_bytes, private_key_hex)
}
src/wallets/create_wallet.rs
// convert the public key to XOR format to use
// as wallet address and add the prefix
pub(crate) fn generate_address(prefix: AddressPrefix, public_key: &str) -> String {
let prefix_str = prefix.to_string();
let public_key_bytes = hex::decode(public_key).expect("Failed to decode public key hex");
let xor_key: Vec<u8> = vec![0x01; public_key_bytes.len()];
// XOR the binary representation with the custom XOR key
let xored_binary: Vec<u8> = public_key_bytes
.iter()
.zip(xor_key.iter())
.map(|(a, b)| a ^ b)
.collect();
// Convert the XORed binary directly to hex
let result_hex: String = xored_binary.iter().map(|&byte| format!("{:02x}", byte)).collect();
format!("{}{}", prefix_str, result_hex)
}
impl Wallet {
pub fn keypair(address_prefix: AddressPrefix) -> Wallet {
// Generate a new key pair
let (public_key, private_key) = generate_keypair();
let address = generate_address(address_prefix, &hex::encode(&public_key));
Wallet {
address,
public_key: hex::encode(public_key),
private_key,
}
}
}