1use crate::crypto::traits::{PublicKey, Signature, Signer, Verifier};
7use crate::error::{AptosError, AptosResult};
8use blst::BLST_ERROR;
9use blst::min_pk::{PublicKey as BlstPublicKey, SecretKey, Signature as BlstSignature};
10use rand::RngCore;
11use serde::{Deserialize, Serialize};
12use std::fmt;
13use zeroize::Zeroize;
14
15pub const BLS12381_PRIVATE_KEY_LENGTH: usize = 32;
17pub const BLS12381_PUBLIC_KEY_LENGTH: usize = 48;
19pub const BLS12381_SIGNATURE_LENGTH: usize = 96;
21pub const BLS12381_POP_LENGTH: usize = 96;
23
24const DST: &[u8] = b"BLS_SIG_BLS12381G2_XMD:SHA-256_SSWU_RO_POP_";
26const DST_POP: &[u8] = b"BLS_POP_BLS12381G2_XMD:SHA-256_SSWU_RO_POP_";
28
29#[derive(Clone, Zeroize)]
36#[zeroize(drop)]
37pub struct Bls12381PrivateKey {
38 inner: SecretKey,
39}
40
41impl Bls12381PrivateKey {
42 pub fn generate() -> Self {
51 let mut ikm = [0u8; 32];
52 rand::rngs::OsRng.fill_bytes(&mut ikm);
53 let secret_key = SecretKey::key_gen(&ikm, &[])
55 .expect("internal error: BLS key generation failed with 32-byte IKM");
56 Self { inner: secret_key }
57 }
58
59 pub fn from_seed(seed: &[u8]) -> AptosResult<Self> {
67 if seed.len() < 32 {
68 return Err(AptosError::InvalidPrivateKey(
69 "seed must be at least 32 bytes".to_string(),
70 ));
71 }
72 let secret_key = SecretKey::key_gen(seed, &[])
73 .map_err(|e| AptosError::InvalidPrivateKey(format!("{e:?}")))?;
74 Ok(Self { inner: secret_key })
75 }
76
77 pub fn from_bytes(bytes: &[u8]) -> AptosResult<Self> {
83 if bytes.len() != BLS12381_PRIVATE_KEY_LENGTH {
84 return Err(AptosError::InvalidPrivateKey(format!(
85 "expected {} bytes, got {}",
86 BLS12381_PRIVATE_KEY_LENGTH,
87 bytes.len()
88 )));
89 }
90 let secret_key = SecretKey::from_bytes(bytes)
91 .map_err(|e| AptosError::InvalidPrivateKey(format!("{e:?}")))?;
92 Ok(Self { inner: secret_key })
93 }
94
95 pub fn from_hex(hex_str: &str) -> AptosResult<Self> {
101 let bytes = const_hex::decode(hex_str)?;
102 Self::from_bytes(&bytes)
103 }
104
105 pub fn to_bytes(&self) -> [u8; BLS12381_PRIVATE_KEY_LENGTH] {
107 self.inner.to_bytes()
108 }
109
110 pub fn to_hex(&self) -> String {
112 const_hex::encode_prefixed(self.inner.to_bytes())
113 }
114
115 pub fn public_key(&self) -> Bls12381PublicKey {
117 Bls12381PublicKey {
118 inner: self.inner.sk_to_pk(),
119 }
120 }
121
122 pub fn sign(&self, message: &[u8]) -> Bls12381Signature {
124 let signature = self.inner.sign(message, DST, &[]);
125 Bls12381Signature { inner: signature }
126 }
127
128 pub fn create_proof_of_possession(&self) -> Bls12381ProofOfPossession {
133 let pk = self.public_key();
134 let pk_bytes = pk.to_bytes();
135 let pop = self.inner.sign(&pk_bytes, DST_POP, &[]);
136 Bls12381ProofOfPossession { inner: pop }
137 }
138}
139
140impl Signer for Bls12381PrivateKey {
141 type Signature = Bls12381Signature;
142
143 fn sign(&self, message: &[u8]) -> Bls12381Signature {
144 Bls12381PrivateKey::sign(self, message)
145 }
146
147 fn public_key(&self) -> Bls12381PublicKey {
148 Bls12381PrivateKey::public_key(self)
149 }
150}
151
152impl fmt::Debug for Bls12381PrivateKey {
153 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
154 write!(f, "Bls12381PrivateKey([REDACTED])")
155 }
156}
157
158#[derive(Clone, PartialEq, Eq)]
160pub struct Bls12381PublicKey {
161 inner: BlstPublicKey,
162}
163
164impl Bls12381PublicKey {
165 pub fn from_bytes(bytes: &[u8]) -> AptosResult<Self> {
171 if bytes.len() != BLS12381_PUBLIC_KEY_LENGTH {
172 return Err(AptosError::InvalidPublicKey(format!(
173 "expected {} bytes, got {}",
174 BLS12381_PUBLIC_KEY_LENGTH,
175 bytes.len()
176 )));
177 }
178 let public_key = BlstPublicKey::from_bytes(bytes)
179 .map_err(|e| AptosError::InvalidPublicKey(format!("{e:?}")))?;
180 Ok(Self { inner: public_key })
181 }
182
183 pub fn from_hex(hex_str: &str) -> AptosResult<Self> {
189 let bytes = const_hex::decode(hex_str)?;
190 Self::from_bytes(&bytes)
191 }
192
193 pub fn to_bytes(&self) -> Vec<u8> {
195 self.inner.compress().to_vec()
196 }
197
198 pub fn to_hex(&self) -> String {
200 const_hex::encode_prefixed(self.inner.compress())
201 }
202
203 pub fn verify(&self, message: &[u8], signature: &Bls12381Signature) -> AptosResult<()> {
209 let result = signature
210 .inner
211 .verify(true, message, DST, &[], &self.inner, true);
212 if result == BLST_ERROR::BLST_SUCCESS {
213 Ok(())
214 } else {
215 Err(AptosError::SignatureVerificationFailed)
216 }
217 }
218}
219
220impl Bls12381PublicKey {
221 pub fn aggregate(public_keys: &[&Bls12381PublicKey]) -> AptosResult<Bls12381PublicKey> {
231 if public_keys.is_empty() {
232 return Err(AptosError::InvalidPublicKey(
233 "cannot aggregate empty list of public keys".to_string(),
234 ));
235 }
236 let blst_pks: Vec<&BlstPublicKey> = public_keys.iter().map(|pk| &pk.inner).collect();
237 let agg_pk = blst::min_pk::AggregatePublicKey::aggregate(&blst_pks, false)
238 .map_err(|e| AptosError::InvalidPublicKey(format!("{e:?}")))?;
239 Ok(Bls12381PublicKey {
240 inner: agg_pk.to_public_key(),
241 })
242 }
243}
244
245impl PublicKey for Bls12381PublicKey {
246 const LENGTH: usize = BLS12381_PUBLIC_KEY_LENGTH;
247
248 fn from_bytes(bytes: &[u8]) -> AptosResult<Self> {
254 Bls12381PublicKey::from_bytes(bytes)
255 }
256
257 fn to_bytes(&self) -> Vec<u8> {
258 Bls12381PublicKey::to_bytes(self)
259 }
260}
261
262impl Verifier for Bls12381PublicKey {
263 type Signature = Bls12381Signature;
264
265 fn verify(&self, message: &[u8], signature: &Bls12381Signature) -> AptosResult<()> {
271 Bls12381PublicKey::verify(self, message, signature)
272 }
273}
274
275impl fmt::Debug for Bls12381PublicKey {
276 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
277 write!(f, "Bls12381PublicKey({})", self.to_hex())
278 }
279}
280
281impl fmt::Display for Bls12381PublicKey {
282 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
283 write!(f, "{}", self.to_hex())
284 }
285}
286
287impl Serialize for Bls12381PublicKey {
288 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
289 where
290 S: serde::Serializer,
291 {
292 if serializer.is_human_readable() {
293 serializer.serialize_str(&self.to_hex())
294 } else {
295 serializer.serialize_bytes(&self.to_bytes())
296 }
297 }
298}
299
300impl<'de> Deserialize<'de> for Bls12381PublicKey {
301 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
302 where
303 D: serde::Deserializer<'de>,
304 {
305 if deserializer.is_human_readable() {
306 let s = String::deserialize(deserializer)?;
307 Self::from_hex(&s).map_err(serde::de::Error::custom)
308 } else {
309 let bytes = Vec::<u8>::deserialize(deserializer)?;
310 Self::from_bytes(&bytes).map_err(serde::de::Error::custom)
311 }
312 }
313}
314
315#[derive(Clone, PartialEq, Eq)]
317pub struct Bls12381Signature {
318 inner: BlstSignature,
319}
320
321impl Bls12381Signature {
322 pub fn from_bytes(bytes: &[u8]) -> AptosResult<Self> {
328 if bytes.len() != BLS12381_SIGNATURE_LENGTH {
329 return Err(AptosError::InvalidSignature(format!(
330 "expected {} bytes, got {}",
331 BLS12381_SIGNATURE_LENGTH,
332 bytes.len()
333 )));
334 }
335 let signature = BlstSignature::from_bytes(bytes)
336 .map_err(|e| AptosError::InvalidSignature(format!("{e:?}")))?;
337 Ok(Self { inner: signature })
338 }
339
340 pub fn from_hex(hex_str: &str) -> AptosResult<Self> {
346 let bytes = const_hex::decode(hex_str)?;
347 Self::from_bytes(&bytes)
348 }
349
350 pub fn to_bytes(&self) -> Vec<u8> {
352 self.inner.compress().to_vec()
353 }
354
355 pub fn to_hex(&self) -> String {
357 const_hex::encode_prefixed(self.inner.compress())
358 }
359}
360
361impl Bls12381Signature {
362 pub fn aggregate(signatures: &[&Bls12381Signature]) -> AptosResult<Bls12381Signature> {
376 if signatures.is_empty() {
377 return Err(AptosError::InvalidSignature(
378 "cannot aggregate empty list of signatures".to_string(),
379 ));
380 }
381 let blst_sigs: Vec<&BlstSignature> = signatures.iter().map(|s| &s.inner).collect();
382 let agg_sig = blst::min_pk::AggregateSignature::aggregate(&blst_sigs, false)
383 .map_err(|e| AptosError::InvalidSignature(format!("{e:?}")))?;
384 Ok(Bls12381Signature {
385 inner: agg_sig.to_signature(),
386 })
387 }
388}
389
390impl Signature for Bls12381Signature {
391 type PublicKey = Bls12381PublicKey;
392 const LENGTH: usize = BLS12381_SIGNATURE_LENGTH;
393
394 fn from_bytes(bytes: &[u8]) -> AptosResult<Self> {
400 Bls12381Signature::from_bytes(bytes)
401 }
402
403 fn to_bytes(&self) -> Vec<u8> {
404 Bls12381Signature::to_bytes(self)
405 }
406}
407
408impl fmt::Debug for Bls12381Signature {
409 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
410 write!(f, "Bls12381Signature({})", self.to_hex())
411 }
412}
413
414impl fmt::Display for Bls12381Signature {
415 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
416 write!(f, "{}", self.to_hex())
417 }
418}
419
420impl Serialize for Bls12381Signature {
421 fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
422 where
423 S: serde::Serializer,
424 {
425 if serializer.is_human_readable() {
426 serializer.serialize_str(&self.to_hex())
427 } else {
428 serializer.serialize_bytes(&self.to_bytes())
429 }
430 }
431}
432
433impl<'de> Deserialize<'de> for Bls12381Signature {
434 fn deserialize<D>(deserializer: D) -> Result<Self, D::Error>
435 where
436 D: serde::Deserializer<'de>,
437 {
438 if deserializer.is_human_readable() {
439 let s = String::deserialize(deserializer)?;
440 Self::from_hex(&s).map_err(serde::de::Error::custom)
441 } else {
442 let bytes = Vec::<u8>::deserialize(deserializer)?;
443 Self::from_bytes(&bytes).map_err(serde::de::Error::custom)
444 }
445 }
446}
447
448#[derive(Clone, PartialEq, Eq)]
453pub struct Bls12381ProofOfPossession {
454 inner: BlstSignature,
455}
456
457impl Bls12381ProofOfPossession {
458 pub fn from_bytes(bytes: &[u8]) -> AptosResult<Self> {
464 if bytes.len() != BLS12381_POP_LENGTH {
465 return Err(AptosError::InvalidSignature(format!(
466 "expected {} bytes, got {}",
467 BLS12381_POP_LENGTH,
468 bytes.len()
469 )));
470 }
471 let pop = BlstSignature::from_bytes(bytes)
472 .map_err(|e| AptosError::InvalidSignature(format!("{e:?}")))?;
473 Ok(Self { inner: pop })
474 }
475
476 pub fn from_hex(hex_str: &str) -> AptosResult<Self> {
482 let bytes = const_hex::decode(hex_str)?;
483 Self::from_bytes(&bytes)
484 }
485
486 pub fn to_bytes(&self) -> Vec<u8> {
488 self.inner.compress().to_vec()
489 }
490
491 pub fn to_hex(&self) -> String {
493 const_hex::encode_prefixed(self.inner.compress())
494 }
495
496 pub fn verify(&self, public_key: &Bls12381PublicKey) -> AptosResult<()> {
504 let pk_bytes = public_key.to_bytes();
505 let result = self
506 .inner
507 .verify(true, &pk_bytes, DST_POP, &[], &public_key.inner, true);
508 if result == BLST_ERROR::BLST_SUCCESS {
509 Ok(())
510 } else {
511 Err(AptosError::SignatureVerificationFailed)
512 }
513 }
514}
515
516impl fmt::Debug for Bls12381ProofOfPossession {
517 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
518 write!(f, "Bls12381ProofOfPossession({})", self.to_hex())
519 }
520}
521
522impl fmt::Display for Bls12381ProofOfPossession {
523 fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
524 write!(f, "{}", self.to_hex())
525 }
526}
527
528#[cfg(test)]
529mod tests {
530 use super::*;
531
532 #[test]
533 fn test_generate_and_sign() {
534 let private_key = Bls12381PrivateKey::generate();
535 let message = b"hello world";
536 let signature = private_key.sign(message);
537
538 let public_key = private_key.public_key();
539 assert!(public_key.verify(message, &signature).is_ok());
540 }
541
542 #[test]
543 fn test_wrong_message_fails() {
544 let private_key = Bls12381PrivateKey::generate();
545 let message = b"hello world";
546 let wrong_message = b"hello world!";
547 let signature = private_key.sign(message);
548
549 let public_key = private_key.public_key();
550 assert!(public_key.verify(wrong_message, &signature).is_err());
551 }
552
553 #[test]
554 fn test_from_bytes_roundtrip() {
555 let private_key = Bls12381PrivateKey::generate();
556 let bytes = private_key.to_bytes();
557 let restored = Bls12381PrivateKey::from_bytes(&bytes).unwrap();
558 assert_eq!(private_key.to_bytes(), restored.to_bytes());
559 }
560
561 #[test]
562 fn test_public_key_from_bytes_roundtrip() {
563 let private_key = Bls12381PrivateKey::generate();
564 let public_key = private_key.public_key();
565 let bytes = public_key.to_bytes();
566 let restored = Bls12381PublicKey::from_bytes(&bytes).unwrap();
567 assert_eq!(public_key.to_bytes(), restored.to_bytes());
568 }
569
570 #[test]
571 fn test_signature_from_bytes_roundtrip() {
572 let private_key = Bls12381PrivateKey::generate();
573 let signature = private_key.sign(b"test");
574 let bytes = signature.to_bytes();
575 let restored = Bls12381Signature::from_bytes(&bytes).unwrap();
576 assert_eq!(signature.to_bytes(), restored.to_bytes());
577 }
578
579 #[test]
580 fn test_hex_roundtrip() {
581 let private_key = Bls12381PrivateKey::generate();
582 let hex = private_key.to_hex();
583 let restored = Bls12381PrivateKey::from_hex(&hex).unwrap();
584 assert_eq!(private_key.to_bytes(), restored.to_bytes());
585 }
586
587 #[test]
588 fn test_public_key_hex_roundtrip() {
589 let private_key = Bls12381PrivateKey::generate();
590 let public_key = private_key.public_key();
591 let hex = public_key.to_hex();
592 let restored = Bls12381PublicKey::from_hex(&hex).unwrap();
593 assert_eq!(public_key.to_bytes(), restored.to_bytes());
594 }
595
596 #[test]
597 fn test_signature_hex_roundtrip() {
598 let private_key = Bls12381PrivateKey::generate();
599 let signature = private_key.sign(b"test");
600 let hex = signature.to_hex();
601 let restored = Bls12381Signature::from_hex(&hex).unwrap();
602 assert_eq!(signature.to_bytes(), restored.to_bytes());
603 }
604
605 #[test]
606 fn test_public_key_length() {
607 assert_eq!(Bls12381PublicKey::LENGTH, BLS12381_PUBLIC_KEY_LENGTH);
608 }
609
610 #[test]
611 fn test_signature_length() {
612 assert_eq!(Bls12381Signature::LENGTH, BLS12381_SIGNATURE_LENGTH);
613 }
614
615 #[test]
616 fn test_invalid_private_key_bytes() {
617 let bytes = vec![0u8; 16]; let result = Bls12381PrivateKey::from_bytes(&bytes);
619 assert!(result.is_err());
620 }
621
622 #[test]
623 fn test_invalid_public_key_bytes() {
624 let bytes = vec![0u8; 16]; let result = Bls12381PublicKey::from_bytes(&bytes);
626 assert!(result.is_err());
627 }
628
629 #[test]
630 fn test_invalid_signature_bytes() {
631 let bytes = vec![0u8; 16]; let result = Bls12381Signature::from_bytes(&bytes);
633 assert!(result.is_err());
634 }
635
636 #[test]
637 fn test_json_serialization_public_key() {
638 let private_key = Bls12381PrivateKey::generate();
639 let public_key = private_key.public_key();
640 let json = serde_json::to_string(&public_key).unwrap();
641 let restored: Bls12381PublicKey = serde_json::from_str(&json).unwrap();
642 assert_eq!(public_key.to_bytes(), restored.to_bytes());
643 }
644
645 #[test]
646 fn test_json_serialization_signature() {
647 let private_key = Bls12381PrivateKey::generate();
648 let signature = private_key.sign(b"test");
649 let json = serde_json::to_string(&signature).unwrap();
650 let restored: Bls12381Signature = serde_json::from_str(&json).unwrap();
651 assert_eq!(signature.to_bytes(), restored.to_bytes());
652 }
653
654 #[test]
655 fn test_proof_of_possession() {
656 let private_key = Bls12381PrivateKey::generate();
657 let public_key = private_key.public_key();
658 let pop = private_key.create_proof_of_possession();
659
660 assert!(pop.verify(&public_key).is_ok());
662
663 let other_key = Bls12381PrivateKey::generate().public_key();
665 assert!(pop.verify(&other_key).is_err());
666 }
667
668 #[test]
669 fn test_pop_bytes_roundtrip() {
670 let private_key = Bls12381PrivateKey::generate();
671 let pop = private_key.create_proof_of_possession();
672
673 let bytes = pop.to_bytes();
674 assert_eq!(bytes.len(), BLS12381_POP_LENGTH);
675
676 let restored = Bls12381ProofOfPossession::from_bytes(&bytes).unwrap();
677 assert_eq!(pop.to_bytes(), restored.to_bytes());
678 }
679
680 #[test]
681 fn test_pop_hex_roundtrip() {
682 let private_key = Bls12381PrivateKey::generate();
683 let pop = private_key.create_proof_of_possession();
684
685 let hex = pop.to_hex();
686 assert!(hex.starts_with("0x"));
687
688 let restored = Bls12381ProofOfPossession::from_hex(&hex).unwrap();
689 assert_eq!(pop.to_bytes(), restored.to_bytes());
690 }
691
692 #[test]
693 fn test_pop_invalid_bytes_length() {
694 let bytes = vec![0u8; 32]; let result = Bls12381ProofOfPossession::from_bytes(&bytes);
696 assert!(result.is_err());
697 }
698
699 #[test]
700 fn test_aggregate_public_keys() {
701 let pk1 = Bls12381PrivateKey::generate().public_key();
702 let pk2 = Bls12381PrivateKey::generate().public_key();
703 let pk3 = Bls12381PrivateKey::generate().public_key();
704
705 let agg = Bls12381PublicKey::aggregate(&[&pk1, &pk2, &pk3]).unwrap();
706 assert!(!agg.to_bytes().is_empty());
707 }
708
709 #[test]
710 fn test_aggregate_public_keys_empty() {
711 let result = Bls12381PublicKey::aggregate(&[]);
712 assert!(result.is_err());
713 }
714
715 #[test]
716 fn test_aggregate_signatures() {
717 let pk1 = Bls12381PrivateKey::generate();
718 let pk2 = Bls12381PrivateKey::generate();
719
720 let message = b"aggregate test";
721 let sig1 = pk1.sign(message);
722 let sig2 = pk2.sign(message);
723
724 let agg_sig = Bls12381Signature::aggregate(&[&sig1, &sig2]).unwrap();
725 assert!(!agg_sig.to_bytes().is_empty());
726 }
727
728 #[test]
729 fn test_aggregate_signatures_empty() {
730 let result = Bls12381Signature::aggregate(&[]);
731 assert!(result.is_err());
732 }
733
734 #[test]
735 fn test_from_seed() {
736 let seed = [42u8; 32];
737 let pk1 = Bls12381PrivateKey::from_seed(&seed).unwrap();
738 let pk2 = Bls12381PrivateKey::from_seed(&seed).unwrap();
739
740 assert_eq!(pk1.to_bytes(), pk2.to_bytes());
742 }
743
744 #[test]
745 fn test_from_seed_too_short() {
746 let seed = [42u8; 16]; let result = Bls12381PrivateKey::from_seed(&seed);
748 assert!(result.is_err());
749 }
750
751 #[test]
752 fn test_private_key_debug() {
753 let private_key = Bls12381PrivateKey::generate();
754 let debug = format!("{private_key:?}");
755 assert!(debug.contains("REDACTED"));
756 assert!(!debug.contains(&private_key.to_hex()));
757 }
758
759 #[test]
760 fn test_public_key_debug() {
761 let private_key = Bls12381PrivateKey::generate();
762 let public_key = private_key.public_key();
763 let debug = format!("{public_key:?}");
764 assert!(debug.contains("Bls12381PublicKey"));
765 }
766
767 #[test]
768 fn test_public_key_display() {
769 let private_key = Bls12381PrivateKey::generate();
770 let public_key = private_key.public_key();
771 let display = format!("{public_key}");
772 assert!(display.starts_with("0x"));
773 }
774
775 #[test]
776 fn test_signature_debug() {
777 let private_key = Bls12381PrivateKey::generate();
778 let signature = private_key.sign(b"test");
779 let debug = format!("{signature:?}");
780 assert!(debug.contains("Bls12381Signature"));
781 }
782
783 #[test]
784 fn test_signature_display() {
785 let private_key = Bls12381PrivateKey::generate();
786 let signature = private_key.sign(b"test");
787 let display = format!("{signature}");
788 assert!(display.starts_with("0x"));
789 }
790
791 #[test]
792 fn test_pop_debug() {
793 let private_key = Bls12381PrivateKey::generate();
794 let pop = private_key.create_proof_of_possession();
795 let debug = format!("{pop:?}");
796 assert!(debug.contains("Bls12381ProofOfPossession"));
797 }
798
799 #[test]
800 fn test_pop_display() {
801 let private_key = Bls12381PrivateKey::generate();
802 let pop = private_key.create_proof_of_possession();
803 let display = format!("{pop}");
804 assert!(display.starts_with("0x"));
805 }
806
807 #[test]
808 fn test_signer_trait() {
809 use crate::crypto::traits::Signer;
810
811 let private_key = Bls12381PrivateKey::generate();
812 let message = b"trait test";
813
814 let signature = Signer::sign(&private_key, message);
815 let public_key = Signer::public_key(&private_key);
816
817 assert!(public_key.verify(message, &signature).is_ok());
818 }
819
820 #[test]
821 fn test_verifier_trait() {
822 use crate::crypto::traits::Verifier;
823
824 let private_key = Bls12381PrivateKey::generate();
825 let public_key = private_key.public_key();
826 let message = b"verifier test";
827 let signature = private_key.sign(message);
828
829 assert!(Verifier::verify(&public_key, message, &signature).is_ok());
830 }
831
832 #[test]
833 fn test_public_key_trait() {
834 use crate::crypto::traits::PublicKey;
835
836 let private_key = Bls12381PrivateKey::generate();
837 let public_key = private_key.public_key();
838 let bytes = PublicKey::to_bytes(&public_key);
839 let restored = Bls12381PublicKey::from_bytes(&bytes).unwrap();
840 assert_eq!(public_key, restored);
841 }
842
843 #[test]
844 fn test_signature_trait() {
845 use crate::crypto::traits::Signature;
846
847 let private_key = Bls12381PrivateKey::generate();
848 let signature = private_key.sign(b"test");
849 let bytes = Signature::to_bytes(&signature);
850 let restored = Bls12381Signature::from_bytes(&bytes).unwrap();
851 assert_eq!(signature, restored);
852 }
853
854 #[test]
855 fn test_zeroize_clears_secret_bytes() {
856 use zeroize::Zeroize;
857
858 let mut private_key = Bls12381PrivateKey::from_seed(&[7u8; 32]).unwrap();
859 assert_ne!(private_key.to_bytes(), [0u8; BLS12381_PRIVATE_KEY_LENGTH]);
861
862 private_key.zeroize();
863
864 assert_eq!(private_key.to_bytes(), [0u8; BLS12381_PRIVATE_KEY_LENGTH]);
866 }
867}