1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66
// Copyright (c) The Diem Core Contributors
// SPDX-License-Identifier: Apache-2.0
// Copyright 2021 Conflux Foundation. All rights reserved.
// Conflux is free software and distributed under GNU General Public License.
// See http://www.gnu.org/licenses/
//! This file implements a KeyPair data structure.
//!
//! The point of a KeyPair is to deserialize a private key into a structure
//! that will only allow the private key to be moved out once
//! (hence providing good key hygiene)
//! while allowing access to the public key part forever.
//!
//! The public key part is dynamically derived during deserialization,
//! while ignored during serialization.
use diem_crypto::PrivateKey;
use serde::{de::DeserializeOwned, Deserialize, Serialize};
/// ConfigKey places a clonable wrapper around PrivateKeys for config purposes
/// only. The only time configs have keys is either for testing or for low
/// security requirements. Diem recommends that keys be stored in key managers.
/// If we make keys unclonable, then the configs must be mutable
/// and that becomes a requirement strictly as a result of supporting test
/// environments, which is undesirable. Hence this internal wrapper allows for
/// keys to be clonable but only from configs.
#[derive(Debug, Deserialize, Serialize)]
pub struct ConfigKey<T: PrivateKey + Serialize> {
// Skip private key serde to avoid printing out private key accidentally
#[serde(skip_serializing, bound(deserialize = "T: Deserialize<'de>"))]
pub(crate) key: T,
}
impl<T: DeserializeOwned + PrivateKey + Serialize> ConfigKey<T> {
pub fn new(key: T) -> Self { Self { key } }
pub fn private_key(&self) -> T { self.clone().key }
pub fn public_key(&self) -> T::PublicKeyMaterial {
diem_crypto::PrivateKey::public_key(&self.key)
}
}
impl<T: DeserializeOwned + PrivateKey + Serialize> Clone for ConfigKey<T> {
fn clone(&self) -> Self {
Self::new(bcs::from_bytes(&bcs::to_bytes(&self.key).unwrap()).unwrap())
}
}
#[cfg(test)]
impl<T: PrivateKey + Serialize + diem_crypto::Uniform> Default
for ConfigKey<T>
{
fn default() -> Self {
Self {
key: diem_crypto::Uniform::generate_for_testing(),
}
}
}
impl<T: PrivateKey + Serialize> PartialEq for ConfigKey<T> {
fn eq(&self, other: &Self) -> bool {
bcs::to_bytes(&self).unwrap() == bcs::to_bytes(&other).unwrap()
}
}