libchat/core/crypto/src/signatures.rs
kaichao cd7dd6a330
feat: http server based key package registry (#124)
* feat: http server based key package registry

* chore: instructions on running the registration service

* chore: remove duplicate post param

* chore: revert out sourced account id for multi devices support

* feat: signature on account id and key packages

* chore: include http registry in contact registry module

* refactor: use device id for retrieve key package

* chore: use string for device id

* feat: server verification on the register

* chore: doc the smoke test

* chore: fix data folder non exist

* chore: use payload for register and retrieve

* chore: fix clippy
2026-06-04 10:09:29 +08:00

90 lines
2.2 KiB
Rust

use ed25519_dalek::{self, Signer};
use rand_core::OsRng;
use std::fmt::Debug;
use thiserror::Error;
#[derive(Debug, Error)]
#[error("verification failed of the Ed25519 Signature")]
pub struct SignatureVerificationError {}
/// A 64-byte XEdDSA signature over an Ed25519-compatible curve.
#[derive(Clone, Copy, Debug, PartialEq, Eq)]
pub struct Ed25519Signature([u8; 64]);
impl Ed25519Signature {
pub fn empty() -> Self {
Self([0u8; 64])
}
}
impl AsRef<[u8; 64]> for Ed25519Signature {
fn as_ref(&self) -> &[u8; 64] {
&self.0
}
}
impl From<[u8; 64]> for Ed25519Signature {
fn from(bytes: [u8; 64]) -> Self {
Self(bytes)
}
}
#[derive(Clone)]
pub struct Ed25519SigningKey(ed25519_dalek::SigningKey);
impl Ed25519SigningKey {
pub fn generate() -> Self {
Self(ed25519_dalek::SigningKey::generate(&mut OsRng))
}
pub fn sign(&self, msg: &[u8]) -> Ed25519Signature {
self.0.sign(msg).to_bytes().into()
}
pub fn verifying_key(&self) -> Ed25519VerifyingKey {
self.0.verifying_key().into()
}
}
impl Debug for Ed25519SigningKey {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
f.debug_tuple("Ed25519SigningKey")
.field(&"[redacted]")
.finish()
}
}
#[derive(Clone, Debug)]
pub struct Ed25519VerifyingKey(ed25519_dalek::VerifyingKey);
impl Ed25519VerifyingKey {
pub fn verify(
&self,
msg: &[u8],
signature: &Ed25519Signature,
) -> Result<(), SignatureVerificationError> {
let inner_signature = signature.0;
self.0
.verify_strict(msg, &ed25519_dalek::Signature::from_bytes(&inner_signature))
.map_err(|_| SignatureVerificationError {})
}
pub fn from_bytes(bytes: &[u8; 32]) -> Result<Self, SignatureVerificationError> {
ed25519_dalek::VerifyingKey::from_bytes(bytes)
.map(Self)
.map_err(|_| SignatureVerificationError {})
}
}
impl From<ed25519_dalek::VerifyingKey> for Ed25519VerifyingKey {
fn from(value: ed25519_dalek::VerifyingKey) -> Self {
Ed25519VerifyingKey(value)
}
}
impl AsRef<[u8]> for Ed25519VerifyingKey {
fn as_ref(&self) -> &[u8] {
self.0.as_bytes()
}
}