Implement display name resolving

master
Valentin Brandl 2020-05-13 16:18:07 +02:00 committed by Denis Kasak
parent 6e5870bd2b
commit d5f66631c1
1 changed files with 65 additions and 0 deletions

View File

@ -180,6 +180,8 @@ pub struct Room {
pub unread_notifications: Option<UInt>, pub unread_notifications: Option<UInt>,
/// The tombstone state of this room. /// The tombstone state of this room.
pub tombstone: Option<Tombstone>, pub tombstone: Option<Tombstone>,
/// The map of display names
display_names: HashMap<UserId, String>,
} }
impl RoomName { impl RoomName {
@ -278,6 +280,7 @@ impl Room {
unread_highlight: None, unread_highlight: None,
unread_notifications: None, unread_notifications: None,
tombstone: None, tombstone: None,
display_names: HashMap::new(),
} }
} }
@ -298,6 +301,11 @@ impl Room {
self.encrypted.as_ref() self.encrypted.as_ref()
} }
/// Get the resolved display name for a member of this room.
pub fn resolved_display_name(&self, id: &UserId) -> Option<&str> {
self.display_names.get(id).map(|s| s.as_str())
}
fn add_member(&mut self, event: &MemberEvent) -> bool { fn add_member(&mut self, event: &MemberEvent) -> bool {
if self if self
.members .members
@ -308,6 +316,63 @@ impl Room {
let member = RoomMember::new(event); let member = RoomMember::new(event);
// find all users that share the same display name as the joining user
let users_with_same_name: Vec<_> = self
.display_names
.iter()
.filter(|(_, v)| {
member
.display_name
.as_ref()
.map(|n| &n == v)
.unwrap_or(false)
})
.map(|(k, _)| k)
.cloned()
.collect();
// if there is no other user with the same display name -> just use the display name
if users_with_same_name.is_empty() {
let display_name = member
.display_name
.as_ref()
.map(|s| s.to_string())
.unwrap_or_else(|| format!("{}", member.user_id));
self.display_names
.insert(member.user_id.clone(), display_name);
} else {
// else user `display_name (userid)`
let users_with_same_name = users_with_same_name
.into_iter()
.filter_map(|id| {
self.members
.get(&id)
.map(|m| {
m.display_name
.as_ref()
.map(|d| format!("{} ({})", d, m.user_id))
.unwrap_or_else(|| format!("{}", m.user_id))
})
.map(|m| (id, m))
})
.collect::<Vec<_>>();
// update all existing users with same name
for (id, member) in users_with_same_name {
self.display_names.insert(id, member);
}
// insert new member's display name
self.display_names.insert(
member.user_id.clone(),
member
.display_name
.as_ref()
.map(|n| format!("{} ({})", n, member.user_id))
.unwrap_or_else(|| format!("{}", member.user_id)),
);
}
self.members self.members
.insert(UserId::try_from(event.state_key.as_str()).unwrap(), member); .insert(UserId::try_from(event.state_key.as_str()).unwrap(), member);