Skip to main content

shadow_crypto/
keypair.rs

1use crate::encryption::EncryptionKey;
2use crate::signature::{SigningKey, VerifyKey};
3use serde::{Deserialize, Serialize};
4
5/// Combined keypair for encryption and signing
6#[derive(Debug)]
7pub struct Keypair {
8    /// Encryption key (X25519 public key)
9    pub encryption_public: [u8; 32],
10    /// Signing key
11    pub signing_key: SigningKey,
12    /// Verification key (public)
13    pub verify_key: VerifyKey,
14}
15
16impl Keypair {
17    /// Generate new keypair
18    pub fn generate() -> Self {
19        let signing_key = SigningKey::generate();
20        let verify_key = signing_key.verify_key();
21        
22        // Generate X25519 keypair (we only store public key here)
23        use x25519_dalek::{EphemeralSecret, PublicKey};
24        let secret = EphemeralSecret::random_from_rng(rand::rngs::OsRng);
25        let encryption_public = PublicKey::from(&secret).to_bytes();
26        
27        Self {
28            encryption_public,
29            signing_key,
30            verify_key,
31        }
32    }
33
34    /// Get public identity (for sharing with peers)
35    pub fn public_identity(&self) -> PublicIdentity {
36        PublicIdentity {
37            encryption_key: self.encryption_public,
38            verify_key: self.verify_key,
39        }
40    }
41}
42
43/// Public identity that can be shared with peers
44#[derive(Debug, Clone, Serialize, Deserialize)]
45pub struct PublicIdentity {
46    /// Public key for encryption (X25519)
47    pub encryption_key: [u8; 32],
48    /// Public key for signature verification (Ed25519)
49    pub verify_key: VerifyKey,
50}
51
52impl PublicIdentity {
53    /// Convert to bytes for network transmission
54    pub fn to_bytes(&self) -> Vec<u8> {
55        bincode::serialize(self).expect("Serialization should not fail")
56    }
57
58    /// Create from bytes
59    pub fn from_bytes(bytes: &[u8]) -> anyhow::Result<Self> {
60        bincode::deserialize(bytes).map_err(Into::into)
61    }
62}
63
64/// Generate a new keypair
65pub fn generate_keypair() -> Keypair {
66    Keypair::generate()
67}
68
69#[cfg(test)]
70mod tests {
71    use super::*;
72
73    #[test]
74    fn test_keypair_generation() {
75        let keypair = generate_keypair();
76        assert_eq!(keypair.encryption_public.len(), 32);
77    }
78
79    #[test]
80    fn test_public_identity_serialization() {
81        let keypair = generate_keypair();
82        let identity = keypair.public_identity();
83        
84        let bytes = identity.to_bytes();
85        let decoded = PublicIdentity::from_bytes(&bytes).unwrap();
86        
87        assert_eq!(identity.encryption_key, decoded.encryption_key);
88        assert_eq!(identity.verify_key.as_bytes(), decoded.verify_key.as_bytes());
89    }
90}