use ruma::{DeviceId, UserId};
use serde::{Deserialize, Serialize};
use crate::olm::{KnownSenderData, SenderData};
#[derive(Debug, Clone, Serialize, Deserialize)]
pub enum ForwarderData {
SenderUnverified(KnownSenderData),
SenderVerified(KnownSenderData),
}
impl TryFrom<&SenderData> for ForwarderData {
type Error = ();
fn try_from(value: &SenderData) -> Result<Self, Self::Error> {
match value {
SenderData::SenderUnverified(known_sender_data) => {
Ok(Self::SenderUnverified(known_sender_data.clone()))
}
SenderData::SenderVerified(known_sender_data) => {
Ok(Self::SenderVerified(known_sender_data.clone()))
}
_ => Err(()),
}
}
}
impl ForwarderData {
pub fn user_id(&self) -> &UserId {
match &self {
ForwarderData::SenderUnverified(known_sender_data)
| ForwarderData::SenderVerified(known_sender_data) => {
known_sender_data.user_id.as_ref()
}
}
}
pub fn device_id(&self) -> Option<&DeviceId> {
match &self {
ForwarderData::SenderUnverified(known_sender_data)
| ForwarderData::SenderVerified(known_sender_data) => {
known_sender_data.device_id.as_deref()
}
}
}
}
#[cfg(test)]
mod tests {
use insta::assert_json_snapshot;
use ruma::{device_id, owned_user_id, user_id};
use vodozemac::Ed25519PublicKey;
use super::ForwarderData;
use crate::olm::{KnownSenderData, SenderData};
#[test]
fn snapshot_forwarder_data() {
insta::with_settings!({prepend_module_to_snapshot => false}, {
assert_json_snapshot!(ForwarderData::SenderUnverified(KnownSenderData {
user_id: owned_user_id!("@foo:bar.baz"),
device_id: None,
master_key: Box::new(Ed25519PublicKey::from_slice(&[1u8; 32]).unwrap()),
}));
assert_json_snapshot!(ForwarderData::SenderVerified(KnownSenderData {
user_id: owned_user_id!("@foo:bar.baz"),
device_id: None,
master_key: Box::new(Ed25519PublicKey::from_slice(&[1u8; 32]).unwrap()),
}));
});
}
#[test]
fn test_deserialize_old_format() {
let master_key = Ed25519PublicKey::from_slice(&[1u8; 32]).unwrap();
let sender_unverified =
SenderData::sender_unverified(user_id!("@u:s.co"), device_id!("DEV"), master_key);
let sender_verified =
SenderData::sender_verified(user_id!("@u:s.co"), device_id!("DEV"), master_key);
let serialized_unverified = serde_json::to_string(&sender_unverified).unwrap();
let serialized_verified = serde_json::to_string(&sender_verified).unwrap();
let deserialized_unverified: ForwarderData =
serde_json::from_str(&serialized_unverified).unwrap();
let deserialized_verified: ForwarderData =
serde_json::from_str(&serialized_verified).unwrap();
assert!(matches!(deserialized_unverified, ForwarderData::SenderUnverified(_)));
assert!(matches!(deserialized_verified, ForwarderData::SenderVerified(_)));
}
#[test]
fn test_try_from_senderdata() {
let master_key = Ed25519PublicKey::from_slice(&[1u8; 32]).unwrap();
let sender_unverified = SenderData::sender_unverified(
user_id!("@test:example.org"),
device_id!("TEST_DEV"),
master_key,
);
let sender_verified = SenderData::sender_verified(
user_id!("@test:example.org"),
device_id!("TEST_DEV"),
master_key,
);
let forwarder_unverified = ForwarderData::try_from(&sender_unverified).unwrap();
let forwarder_verified = ForwarderData::try_from(&sender_verified).unwrap();
assert!(matches!(forwarder_unverified, ForwarderData::SenderUnverified(_)));
assert!(matches!(forwarder_verified, ForwarderData::SenderVerified(_)));
assert!(
ForwarderData::try_from(&SenderData::unknown()).is_err(),
"We should not be able to convert a non-trusted SenderData to a ForwarderData"
);
}
}