use ruma_macros::{Event, EventContent};
use serde::{Deserialize, Serialize};
use crate::{MilliSecondsSinceUnixEpoch, OwnedRoomId, OwnedServerName, OwnedUserId};
#[derive(Clone, Debug, Default, Deserialize, Serialize, EventContent)]
#[cfg_attr(not(feature = "unstable-exhaustive-types"), non_exhaustive)]
#[ruma_event(type = "m.space.child", kind = State, state_key_type = OwnedRoomId)]
pub struct SpaceChildEventContent {
#[serde(skip_serializing_if = "Option::is_none")]
pub via: Option<Vec<OwnedServerName>>,
#[serde(skip_serializing_if = "Option::is_none")]
pub order: Option<String>,
#[serde(skip_serializing_if = "Option::is_none")]
pub suggested: Option<bool>,
}
impl SpaceChildEventContent {
pub fn new() -> Self {
Self::default()
}
}
#[derive(Clone, Debug, Event)]
#[cfg_attr(not(feature = "unstable-exhaustive-types"), non_exhaustive)]
pub struct HierarchySpaceChildEvent {
pub content: SpaceChildEventContent,
pub sender: OwnedUserId,
pub state_key: String,
pub origin_server_ts: MilliSecondsSinceUnixEpoch,
}
#[cfg(test)]
mod tests {
use js_int::uint;
use matches::assert_matches;
use serde_json::{from_value as from_json_value, json, to_value as to_json_value};
use super::{HierarchySpaceChildEvent, SpaceChildEventContent};
use crate::{server_name, user_id, MilliSecondsSinceUnixEpoch};
#[test]
fn space_child_serialization() {
let content = SpaceChildEventContent {
via: Some(vec![server_name!("example.com").to_owned()]),
order: Some("uwu".to_owned()),
suggested: Some(false),
};
let json = json!({
"via": ["example.com"],
"order": "uwu",
"suggested": false,
});
assert_eq!(to_json_value(&content).unwrap(), json);
}
#[test]
fn space_child_empty_serialization() {
let content = SpaceChildEventContent { via: None, order: None, suggested: None };
let json = json!({});
assert_eq!(to_json_value(&content).unwrap(), json);
}
#[test]
fn hierarchy_space_child_serialization() {
let event = HierarchySpaceChildEvent {
content: SpaceChildEventContent {
via: Some(vec![server_name!("example.com").to_owned()]),
order: Some("uwu".to_owned()),
suggested: None,
},
sender: user_id!("@example:localhost").to_owned(),
state_key: "!child:localhost".to_owned(),
origin_server_ts: MilliSecondsSinceUnixEpoch(uint!(1_629_413_349)),
};
let json = json!({
"content": {
"via": ["example.com"],
"order": "uwu",
},
"sender": "@example:localhost",
"state_key": "!child:localhost",
"origin_server_ts": 1_629_413_349,
"type": "m.space.child",
});
assert_eq!(to_json_value(&event).unwrap(), json);
}
#[test]
fn hierarchy_space_child_deserialization() {
let json = json!({
"content": {
"via": [
"example.org"
]
},
"origin_server_ts": 1_629_413_349,
"sender": "@alice:example.org",
"state_key": "!a:example.org",
"type": "m.space.child"
});
assert_matches!(
from_json_value::<HierarchySpaceChildEvent>(json).unwrap(),
HierarchySpaceChildEvent {
content: SpaceChildEventContent {
via: Some(via),
order: None,
suggested: None,
},
origin_server_ts,
sender,
state_key,
} if via[0] == "example.org"
&& origin_server_ts.get() == uint!(1_629_413_349)
&& sender == "@alice:example.org"
&& state_key == "!a:example.org"
);
}
}