hightower_node/
certificates.rs

1use hightower_wireguard::crypto::{PrivateKey, PublicKey25519, dh_generate};
2use serde::{Deserialize, Serialize};
3
4#[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize)]
5pub struct NodeCertificate {
6    #[serde(with = "serde_bytes")]
7    private_key: PrivateKey,
8    #[serde(with = "serde_bytes")]
9    public_key: PublicKey25519,
10}
11
12impl NodeCertificate {
13    pub fn from_keys(private_key: PrivateKey, public_key: PublicKey25519) -> Self {
14        Self {
15            private_key,
16            public_key,
17        }
18    }
19
20    #[cfg_attr(not(test), allow(dead_code))]
21    pub fn private_key(&self) -> &PrivateKey {
22        &self.private_key
23    }
24
25    #[cfg_attr(not(test), allow(dead_code))]
26    pub fn public_key(&self) -> &PublicKey25519 {
27        &self.public_key
28    }
29
30    pub fn private_key_hex(&self) -> String {
31        hex::encode(self.private_key)
32    }
33
34    pub fn public_key_hex(&self) -> String {
35        hex::encode(self.public_key)
36    }
37}
38
39pub fn generate() -> NodeCertificate {
40    let (private_key, public_key) = dh_generate();
41    NodeCertificate::from_keys(private_key, public_key)
42}
43
44#[cfg(test)]
45mod tests {
46    use super::*;
47
48    #[test]
49    fn from_keys_stores_values() {
50        let private_key = [1u8; 32];
51        let public_key = [2u8; 32];
52
53        let cert = NodeCertificate::from_keys(private_key, public_key);
54
55        assert_eq!(cert.private_key(), &private_key);
56        assert_eq!(cert.public_key(), &public_key);
57    }
58
59    #[test]
60    fn private_key_hex_encodes_key() {
61        let private_key = [0xAAu8; 32];
62        let public_key = [0u8; 32];
63        let cert = NodeCertificate::from_keys(private_key, public_key);
64
65        assert_eq!(
66            cert.private_key_hex(),
67            "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa"
68        );
69    }
70
71    #[test]
72    fn public_key_hex_encodes_key() {
73        let private_key = [0u8; 32];
74        let public_key = [0xBBu8; 32];
75        let cert = NodeCertificate::from_keys(private_key, public_key);
76
77        assert_eq!(
78            cert.public_key_hex(),
79            "bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb"
80        );
81    }
82
83    #[test]
84    fn generate_returns_random_keys() {
85        let cert = generate();
86
87        assert_eq!(cert.private_key().len(), 32);
88        assert_eq!(cert.public_key().len(), 32);
89        assert_eq!(cert.private_key_hex().len(), 64);
90        assert_eq!(cert.public_key_hex().len(), 64);
91    }
92
93    #[test]
94    fn serde_round_trip_preserves_data() {
95        let cert = NodeCertificate::from_keys([3u8; 32], [4u8; 32]);
96        let bytes = serde_json::to_vec(&cert).expect("serialize");
97        let decoded: NodeCertificate = serde_json::from_slice(&bytes).expect("deserialize");
98        assert_eq!(decoded, cert);
99    }
100}