Skip to content
118 changes: 115 additions & 3 deletions crates/matrix-sdk-base/src/room/members.rs
Original file line number Diff line number Diff line change
Expand Up @@ -215,9 +215,15 @@ impl RoomMember {
room_info;

let display_name = event.display_name();
let display_name_ambiguous = users_display_names
.get(&display_name)
.is_some_and(|s| is_display_name_ambiguous(&display_name, s));
let membership = event.membership();

println!("{:?} {:?}", users_display_names, &display_name);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should be removed.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ok I will update is_display_name_ambiguous to take a MemberEvent instead of a string

let display_name_ambiguous = users_display_names.get(&display_name).is_some_and(|s| {
if !is_display_name_ambiguous(&display_name, s) {
return false;
}
matches!(*membership, MembershipState::Join | MembershipState::Invite)
});
let is_ignored = ignored_users.as_ref().is_some_and(|s| s.contains(event.user_id()));

Self {
Expand Down Expand Up @@ -478,10 +484,26 @@ pub fn normalize_power_level(power_level: Int, max_power_level: i64) -> Int {

#[cfg(test)]
mod tests {
use std::sync::Arc;

use proptest::prelude::*;

use matrix_sdk_test::{async_test, event_factory::EventFactory};
use ruma::{room_id, user_id};

use super::*;

use crate::{RoomState, StateChanges, StateStore, store::MemoryStore};

fn make_room_test_helper(room_type: RoomState) -> (Arc<MemoryStore>, Room) {
let store = Arc::new(MemoryStore::new());
let user_id = user_id!("@me:example.org");
let room_id = room_id!("!test:localhost");
let (sender, _receiver) = tokio::sync::broadcast::channel(1);

(store.clone(), Room::new(user_id, store, room_id, room_type, sender))
}

prop_compose! {
fn arb_int()(id in any::<i64>()) -> Int {
id.try_into().unwrap_or_default()
Expand Down Expand Up @@ -526,4 +548,94 @@ mod tests {
assert!(normalized >= 0);
assert!(normalized <= 100);
}

#[async_test]
async fn test_room_member_from_parts() {
let (store, room) = make_room_test_helper(RoomState::Joined);

let carol = user_id!("@carol:example.org");
let denis = user_id!("@denis:example.org");
let erica = user_id!("@erica:example.org");
let fred = user_id!("@fred:example.org");
let fredo = user_id!("@fredo:example.org");
let bob = user_id!("@bob:example.org");
let julie = user_id!("@julie:example.org");
let me = user_id!("@me:example.org");
let mewto = user_id!("@mewto:example.org");

let mut changes = StateChanges::new("".to_owned());

let f = EventFactory::new().room(room_id!("!test:localhost"));

{
let members = changes
.state
.entry(room.room_id().to_owned())
.or_default()
.entry(StateEventType::RoomMember)
.or_default();

let ambiguity_maps = changes
.ambiguity_maps
.entry(room.room_id().to_owned())
.or_default();


let display_name = DisplayName::new("Carol");
members.insert(carol.into(), f.member(carol).display_name("Carol").into());
ambiguity_maps.entry(display_name).or_default().insert(carol.to_owned());

let display_name = DisplayName::new("Fred");
members.insert(fred.into(), f.member(fred).display_name("Fred").into());
ambiguity_maps.entry(display_name.clone()).or_default().insert(fred.to_owned());
members.insert(
fredo.into(),
f.member(fredo).display_name("Fred").membership(MembershipState::Knock).into(),
);
ambiguity_maps.entry(display_name.clone()).or_default().insert(fredo.to_owned());
members.insert(
denis.into(),
f.member(denis).display_name("Fred").membership(MembershipState::Leave).into(),
);
ambiguity_maps.entry(display_name.clone()).or_default().insert(erica.to_owned());
members.insert(
erica.into(),
f.member(erica).display_name("Fred").membership(MembershipState::Ban).into(),
);

let display_name = DisplayName::new("Bob");
members.insert(
bob.into(),
f.member(bob).display_name("Bob").membership(MembershipState::Invite).into(),
);
ambiguity_maps.entry(display_name.clone()).or_default().insert(bob.to_owned());
members.insert(julie.into(), f.member(me).display_name("Bob").into());
ambiguity_maps.entry(display_name.clone()).or_default().insert(julie.to_owned());

let display_name = DisplayName::new("Me");
members.insert(me.into(), f.member(me).display_name("Me").into());
ambiguity_maps.entry(display_name.clone()).or_default().insert(me.to_owned());
members.insert(mewto.into(), f.member(mewto).display_name("Me").into());
ambiguity_maps.entry(display_name.clone()).or_default().insert(mewto.to_owned());


store.save_changes(&changes).await.unwrap();
}

assert!(!room.get_member(carol).await.unwrap().expect("Carol user").name_ambiguous());

assert!(!room.get_member(fred).await.unwrap().expect("Fred user").name_ambiguous());
assert!(!room.get_member(fredo).await.unwrap().expect("Fredo user").name_ambiguous());
assert!(!room.get_member(denis).await.unwrap().expect("Denis user").name_ambiguous());
assert!(!room.get_member(erica).await.unwrap().expect("Erica user").name_ambiguous());

assert!(!room.get_member(bob).await.unwrap().expect("Bob user").name_ambiguous());

assert!(!room.get_member(julie).await.unwrap().expect("Julie user").name_ambiguous());
assert!(!room.get_member(bob).await.unwrap().expect("Bob user").name_ambiguous());


assert!(room.get_member(me).await.unwrap().expect("Me user").name_ambiguous());
assert!(room.get_member(mewto).await.unwrap().expect("Mewto user").name_ambiguous());
}
}